Для начала вы должны включить SoftDeletes, после чего вы сможете просматривать записи, помеченные к удалению. В противном случае, вы их не увидите. По умолчанию, для файлов DBF, SoftDeletes установлен в False. Вот логика работы:

procedure TForm1.Button1Click(Sender: TObject);
var
B: BOOL;
W: Word;
begin
Check(DbiSetProp(hDBIObj(Table1.Handle), curSOFTDELETEON,
longint(True)));
{ Проверяем, что это работает }
Check(DbiGetProp(hDBIObj(Table1.Handle), curSOFTDELETEON, @B,
sizeof(B), W));
if B = False then
Label2.Caption := ‘Не помечена’
else
Label2.Caption := ‘Помечена’;
end;

Когда указатель на запись указывает на запись, которую вы хотите удалить, используйте следующую логику:

Table1.UpdateCursorPos;
Check(DbiUndeleteRecord(Table1.Handle));

Метод UpdateCursorPos устанавливает основной курсор BDE на позицию курсора текущей записи, который существуют только для того, чтобы все работало правильно. Вам нужно только вызвать этот метод прямым вызовом одной из BDE API функций (такой как, например, DbiUndeleteRecord).

Ну и, наконец, чтобы все работало, поместите модули DBIPROCS и DBITYPES с список USES.

Автор: admin | в 3:15 | Рубрики: Базы данных

Введение

Индексы для таблиц dBASE могут базироваться на значениях из отдельной области, нередактируемых данных, или на основе выражений. Индексы выражений, уникальные для индексов dBASE, могут формироваться на основе нескольких полей, измененных значений полей или их комбинаций. Выражение для dBASE-индекса создаются с использованием dBASE-функций и синтаксиса для конкатенации нескольких полей или изменения значений поля для полей, включенных в выражения индекса.

В конце данного совета включены два небольших раздела, описывающих механику создания индексов выражений dBASE, один относится к утилите Database Desktop, другой - к приложениям Delphi.
Читать полностью…

Автор: admin | в 3:15 | Рубрики: Базы данных

Во время выполнения программы мне необходимо получать размеры и десятичные порядки полей таблицы DBase.

Следующий код иллюстрирует необходимые вызовы BDE:

procedure GetdBaseFieldTypes(t: TTable; var l: TStringList);
var
pF: pFLDDesc;
cProps: CURProps;
p: pFLDDesc;
i: Byte;
w: Word;
s: string;
oldmode: LongInt;
begin
Check(DbiGetCursorProps(t.Handle, cProps));
Check(DbiGetProp(hDBIObj(t.Handle), curXLTMODE, oldmode, SizeOf(LongInt), w));
Check(DbiSetProp(hDBIObj(t.Handle), curXLTMODE, LongInt(xltNONE)));
try
if MaxAvail < (cProps.iFields * SizeOf(FLDDesc)) then
raise EOutofMemory.Create(’Недостаточно памяти для процесса’);
GetMem(pF, (cProps.iFields * SizeOf(FLDDesc)));
Check(DbiGetFieldDescs(t.Handle, pF));
p := pF;
for i := 1 to cProps.iFields do
begin
with p^ do
begin
s := IntToStr(iFldNum) + ‘ : ‘ + StrPas(szName) + ‘ : ‘;
case iFldType of
fldDBCHAR:
begin { Char string, строка символов }
s := s + ‘CHARACTER(’ + IntToStr(iUnits1) + ‘)’;
end;
fldDBNUM:
begin { Number, число }
s := s + ‘NUMBER(’ + IntToStr(iUnits1) + ‘,’ + InttoStr(iUnits2) +
‘)’;
end;
fldDBMEMO:
begin { Memo (blob), МEMO-BLOB-поле }
s := s + ‘MEMO’;
end;
fldDBBOOL:
begin { Logical, лочическая величина }
s := s + ‘LOGICAL’;
end;
fldDBDATE:
begin { Date, поле даты }
s := s + ‘DATE’;
end;
fldDBFLOAT:
begin { Float, числа с плавающей точкой }
s := s + ‘FLOAT(’ + IntToStr(iUnits1) + ‘,’ + InttoStr(iUnits2) +
‘)’;
end;
fldDBLOCK:
begin { Логический тип LOCKINFO }
s := s + ‘LOCKINFO’;
end;
fldDBOLEBLOB:
begin { OLE object (blob), OLE-объект, BLOB-поле }
s := s + ‘OLE’;
end;
fldDBBINARY:
begin { Binary data (blob), двоичные данные, BLOB-поле }
s := s + ‘BINARY’;
end;
else
s := s + ‘НЕИЗВЕСТНО’;
end;
end;
l.Add(s);
Inc(p);
end;
finally
Check(DbiSetProp(hDBIObj(t.Handle), curXLTMODE, oldmode));
FreeMem(pF, (cProps.iFields * SizeOf(FLDDesc)));
end;
end;

Таблицы dBASE применяют довольно статическую систему нумерации записей. Номер записи для данной записи (извините за тавтологию) отражает физическую позицию в табличном файле. Эти номера записей не изменяются вследствие фильтрации, упорядочивания данных или сортировки. К примеру, первая запись, хранящаяся в .DBF файле, будет иметь номер записи 1. Возможно, после некоторого упорядочивания индекса, запись будет последней из 100 записей. В этом случае запись должна оставаться с тем же номером, а не номером 100, отражающим новую позицию в сортированном наборе данных. Это противоречит таблицам Paradox, где соблюдается последовательная нумерация. Последовательная нумерация Paradox похожа на нумерацию записей dBASE, за исключением большей гибкости и отражению в номере записи ее текущей позиции в наборе данных. То есть, запись может не всегда иметь номер, установленный для нее фильтром набора данных, уменьшившим общее число записей, или при активном индексе, из-за чего может измениться отображаемый порядок записи.
Читать полностью…

Автор: admin | в 3:15 | Рубрики: Базы данных

После удаления записи из таблицы (dBase), возможно ли ее восстановить? Какие идеи?

function GetTableCursor(oTable: TTable): hDBICur;
var
szTable: array[0..78] of Char;
begin
StrPCopy(szTable, oTable.TableName);
DbiGetCursorForTable(oTable.DBHandle, szTable, nil, Result);
end;

function dbRecall(oTable: TTable): DBIResult;
begin
Result := DbiUndeleteRecord(GetTableCursor(oTable)));
end;

Могли бы вы дать пример использования функции?

Предположим, у вас на форме имеется кнопка (с именем ‘butRecall’), восстанавливающая текущую отображаемую (или позиционируемую курсором) запись, данный код, будучи расположенный в обработчике события кнопки OnClick (вместе с опубликованным выше кодом), это демонстрирует (продвигаясь в наших предположених дальше, имя вашего объекта TTable - Table1 и имя текущей формы - Form1):

procedure TForm1.butRecallClick(Sender : TObject);
begin
if dbRecall( Table1 ) <> DBIERR_NONE then
ShowMessage( ‘Не могу восстановить запись!’ );
end;