b := Lo(i shr 16); ShowMessage(Format("%.2x",[b])); {F0; 这是从右数第三个字节} b := Hi(i shr 16); ShowMessage(Format("%.2x",[b])); {7F; 这是从右数第四个字节}
{当然 i 的第四个字节也可以这样提取:} b := Lo(i shr 24); ShowMessage(Format("%.2x",[b])); {7F; 这是从右数第四个字节}
{现在换个思路, 假如没有 Lo 和 Hi 函数, 我们能做到吗? 当然能:} b := (i and $FF); ShowMessage(Format("%.2x",[b])); {FF; 这是从右数第一个字节} b := (i shr 8 and $FF); ShowMessage(Format("%.2x",[b])); {0F; 这是从右数第二个字节} b := (i shr 16 and $FF); ShowMessage(Format("%.2x",[b])); {F0; 这是从右数第三个字节} b := (i shr 24 and $FF); ShowMessage(Format("%.2x",[b])); {7F; 这是从右数第四个字节}
{这是为什么? 换个语句块仔细分析} end;
//关于上面例子的补充: var b: Byte; begin {我们知道 Byte 的最大值是 255, 也就是十六进制的 $FF, 二进制的 11111111} {这个 $FF 有这么个特殊用途:} b := 0 and $FF; ShowMessage(IntToStr(b)); {0} b := 1 and $FF; ShowMessage(IntToStr(b)); {1} b := 100 and $FF; ShowMessage(IntToStr(b)); {100} b := 255 and $FF; ShowMessage(IntToStr(b)); {255} {0..255 直接的任何数与 $FF 进行 and 运算后, 值不变(这从二进制的角度不难理解)}
{现在上面的例子应该可以理解了} end;回到主题://本例中我们把最低位叫第 0 位; 把 Integer 的最高位叫第 31 位. var i: Integer; b: Byte; begin {还是用第一个例子中的值吧:} i := 2146439167; {现在 i 的二进制表示是: 01111111 11110000 00001111 11111111}
{一个字节的最大值是 $FF; 一个二进制位的最大值当然是 1, 写成十六进制还是 $1 } {提取第 0 位:} b := i and 1; ShowMessage(IntToStr(b)); {1} {提取第 0 位也可以写作(右移0位就是没动):} b := i shr 0 and 1; ShowMessage(IntToStr(b)); {1}
{提取第 1 位:} b := i shr 1 and 1; ShowMessage(IntToStr(b)); {1}
{提取第 13 位:} b := i shr 13 and 1; ShowMessage(IntToStr(b)); {0}
{提取最高位(第 31 位):} b := i shr 31 and 1; ShowMessage(IntToStr(b)); {0} end;
//假如只判断最高位, 是 0 还是 1(也就是判断正负), 还可以这样: var i: Integer; begin i := MaxInt; {这肯定是个正数} if i shr 31 = 0 then ShowMessage("正"); {正}
i := -1; if i shr 31 = 1 then ShowMessage("负"); {负} end;