Меня эта тема уже достала. Может, я такой тупой.
Server Version: WI-V2.0.0.12745 Firebird 2.0 Release Candidate 5 CS
Страницы по 8К
UDF-ка
Обратите внимание - я объявляю на выходе 13 символов, а беру памяти 14.
Надеюсь, это правильно.
type
cnumber=string[13];
function ib_util_malloc(Size: Integer): PChar; cdecl; external
'ib_util.dll';
//DECLARE EXTERNAL FUNCTION ITOA32
// BIGINT
//RETURNS CSTRING(13) FREE_IT
//ENTRY_POINT 'itoa32' MODULE_NAME 'udf_itoa32.dll'
function itoa32(var v: Int64):PChar;cdecl;export;
var i,b,l:Byte;
m,n,r:Int64;
st:cnumber;
begin // входное число переворачивается,
//и переводится в типа число по основанию 32
m:=1;
n:=$8000000000000000;
r:=0;
for i:=0 to 63 do begin
if (m and v)<>0 then r:=r or n;
m:=m shl 1;
n:=n shr 1;
end;
b:=(r and $0F);
b:=(b shl 1)+$30;
if b>$39 then Inc(b,7);
l:=12;
st[13]:=chr(b);
r:=r shr 4;
for i:=0 to 11 do begin
b:=(r and $1F)+$30;
if b>$39 then Inc(b,7);
st[l]:=chr(b);
Dec(l);
r:=r shr 5;
end;
Result:=ib_util_malloc(14);
StrPCopy(Result,st);
end;
exports
itoa32;
begin
isMultiThread:=True;
end.
Потом делается таблица
CREATE GENERATOR TST_ID;
CREATE TABLE TST (
ID BIGINT,
CID CHAR(13));
CREATE TRIGGER TST_BI FOR TST
ACTIVE BEFORE INSERT POSITION 0
as
begin
NEW.ID = GEN_ID(TST_ID,1);
new.cid=itoa32(new.id);
end
Потом разными путями загоняю в таблицу 3.6 млн записей.
И когда они уже есть, дается команда
insert into tst (id) select first 3600000 id from tst
Записи заливаются.
Но в некоторых нет cid, там пусто.
ID Разность с предыдущим ID.
3909036
4342965 433929
4776892 433927
5210820 433928
5644749 433929
6078676 433927
6512605 433929
6946532 433927
После этого спокойно проходит команда
update tst set cid=itoa32(id) where coalesce(cid,'')=''
и уже накладывается уникальный индекс на cid.
В логе ничего нет.
Где глюк?