sz 是一个字符数组,还有指向缓冲区中的 memset 是什么?如何将以下 C++ 代码转换为 Delphi?

int data = _ttoi(m_Strtag.GetBuffer(0));
unsigned char sz[4];
memset(sz,0, 4);
sz[0] = (unsigned char)((data >> 24) & 0xFF);
sz[1] = (unsigned char)((data >> 16) & 0xFF);
sz[2] = (unsigned char)((data >> 8) & 0xFF);
sz[3] = (unsigned char)(data & 0xFF);

这是德尔福调用:
如果 SAAT_YTagSelect(hp, isenable, 1, sz, 4) 那么 ...

对于以下 delphi 函数:
function SAAT_YTagSelect(pHandle: Pointer; nOpEnable1, nMatchType: Byte; MatchData: PByte; nLenth: Byte): Boolean; stdcall;

最佳答案

memset 的等价物是 FillChar 并用字节值填充字节范围。

由于数组sz中的所有字节都是在data的字节顺序颠倒时设置的,所以可以去掉这一行。

字节反转可以稍微简化(用类型限制替换 and $FF):

data := StrToInt(aString);
sz[0] := Byte(data shr 24);
sz[1] := Byte(data shr 16);
sz[2] := Byte(data shr 8);
sz[3] := Byte(data);

通过用 Byte() 封闭赋值,编译器被告知跳过范围检查。
生成的汇编代码(带范围检查)的比较表明这也产生了更有效的代码:
Project1.dpr.36: sz[0] := Byte(data shr 24);
0041C485 A1BC3E4200       mov eax,[$00423ebc]
0041C48A C1E818           shr eax,$18
0041C48D A2C03E4200       mov [$00423ec0],al


Project1.dpr.40: sz[0] := (data shr 24) and $FF;
0041C485 A1BC3E4200       mov eax,[$00423ebc]
0041C48A C1E818           shr eax,$18
0041C48D 25FF000000       and eax,$000000ff
0041C492 3DFF000000       cmp eax,$000000ff
0041C497 7605             jbe $0041c49e
0041C499 E8F290FEFF       call @BoundErr
0041C49E A2C03E4200       mov [$00423ec0],al

一种更直接的填充 sz 数组的方法,无需位移例程:
sz[0] := PByte(@data)[3];
sz[1] := PByte(@data)[2];
sz[2] := PByte(@data)[1];
sz[3] := PByte(@data)[0];

关于c++ - Delphi 相当于 C++ 的 memset 是什么?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/26869152/

10-13 06:54