我正在做一个项目,我正在读取内存位置并需要以 ASCII 输出它们的十六进制值。
该语言给了我一个 16 位的字长,所以我需要一次分割来抓取一个半字节来转换为十六进制。不幸的是,该语言只为数学/逻辑函数提供和、或、不和添加。
我想我可以通过左移并测试负标志以在移位后在末尾添加 1 来创建所需的效果,但我认为必须有更好的方法来做到这一点。
任何见解将不胜感激。
使用AND
您可以将所有位设置为零,除了最后一个有效半字节:
0101010111010101
0000000000001111 AND
----------------
0000000000000101
通过将整个内容向右移动,您可以阅读下一个半字节:
0101010111010101 SHR 4
----------------
010101011101
0000000000001111 AND
----------------
0000000000001101
这对你有用吗?
你有带进位的加法吗?代替负测试,将位添加到末尾并添加一个带进位的零以将其放回右侧。并没有真正节省多少。到目前为止,我想不出另一种解决方案,向左移动,测试一下,如果 set add 1 to something 并移动它:
uint a,b,i;
b=0;
for(i=0;i<4;i++)
{
b=b+b;
if(a&0x8000) b+=1;
a=a+a;
}
如果上面的 uint 是 16 位,那么上面会给你一个 12 的右移。a 将在创建 b 的过程中被破坏,如所写。
您可以反过来尝试:您可以使用蛮力,而不是尝试实现右移。这是最高半字节的示例:
unsigned rez, tmp;
for (rez = 0, tmp = some_word & 0x0FFF; tmp != some_word; rez++, tmp += 0x1000);
所以我使用的原始方法奏效了。我还想出了另一个,以防有人再次遇到这个问题。
我构建了一个子程序,它一次评估 4 位并根据评估创建一个数字,对于一些 C 风格的伪代码,它看起来像这样:
16bitSignedInt bin; //binary being analyzed
int value; //number being built
for (int i = 0; i < 4; i++) // while 0-3, for each nibble of the 16 bits
{
if (bin.bit15 = 1)
value += 8; // dominate bit in nibble
bin <<= 1; // left shift 1
if (bin.bit15 = 1)
value += 4; // 2nd bit in nibble
bin <<= 1; // left shift 1
if (bin.bit15 = 1)
value += 2; // 3rd bit in nibble
bin <<= 1; // left shift 1
if (bin.bit15 = 1)
value += 1; // last bit in nibble
bin <<= 1; // left shift 1
//do work with value
}
粗鲁,但有效。