当前位置: 代码迷 >> 汇编语言 >> 微软公司的一道汇编笔试题,大家来做做!该怎么处理
  详细解决方案

微软公司的一道汇编笔试题,大家来做做!该怎么处理

热度:8201   发布时间:2013-02-26 00:00:00.0
微软公司的一道汇编笔试题,大家来做做!
array1是一个由32个16进制位组成的无符号整数变量,假设其已经初始化。请试着在32位机器上,将其转换成十进制数,并将转化后结果的ASCII码按从低位到高位的顺序依次存入array2变量中。例如:array2[0]存放个位,array2[1]存放十位,以此类推。因为array2的长度有富裕,要求转化完成后,用EDI存放转化后十进制数最高位在array2数组中的下标。array1和array2的定义如下:
DATAS   SEGMENT
        array1   DB   16   DUP(0)
        array2   DB   50   DUP(0)  
DATAS   ENDS

题目就是如此,是我的一个朋友给我发过来的,据他说是微软的笔试题,是真是假我没有考证过,但感觉这道题不错,贴出来供大家学习,研究!

------解决方案--------------------------------------------------------
恩,虽然我不会,但我还是帮你顶起来,在很多csdn场合看见你,高手,学习中
------解决方案--------------------------------------------------------
这个貌似一个的计算题。
从高位往下来
例如第一位是 16^0 mod 10=1
第2位是 16^1 mod 10=6
第三位是 16^2 mod 10=6
所以,个位对应的是16位的a1*1+a2*6+a3*6..
a1,a2,a3...代表16位的值
10位是((16^0-1)/10)mod10=0
((16^1-6)/10)mod10=0
..
最后会得到一个数组。
这个数组代表着个位数组,10位数组。。。
但这个数组还是一个16进制的。但是数值从很大的数简化为较小的数。
然后递归几次,就可以被寄存器装下了。这时候再进行常规的10进制计算就可以了。
我的汇编才开始学。不过我认为汇编的麻烦之处在于遇到大数寄存器不够。简化到寄存器可以容纳就万事ok了。
貌似还有更简单的方法。我正在考虑。如果汇编这样麻烦就恶心死我了。
------解决方案--------------------------------------------------------
其实这道题目考的主要是算法与技巧方面,除了复杂以外,难度似乎不太大,我正在考虑有没有解决这道题目的捷径。捷径思想源自十六进制到八进制的转化,就是一个16进制位对应4个2进制位,一个8进制位对应3个二进制位。如果能通过这种方法解决这个问题,那么效率的提升是显而易见的。
---------------------------------------------------------
正如他说的,如果是整数倍就好办了,但10进制和16不是整数倍,因此,高位会影响到低位。如果解决高位影响到地位这正是这道题考查点。
另外,我开始想到的是利用缓存来存储高位对低位的影响,到后来发现,还是麻烦,因为高位的余数叠加,肯定存在进位的情况,如果进位数大于寄存器还是麻烦事情。因此使用了多组。
如果位数比较少,则可以使用直接存在一维数组中,计算完在10进制整合,这当然就简单多了。
------解决方案--------------------------------------------------------
回头看看了,写的有点乱了,呵呵。
思路简单的说就是把所有影响到个位的数字提取出来,然后把影响到十位的提取出来。。。
最后在进行进位整合。
------解决方案--------------------------------------------------------
同意LZ的观点,16进制转10进制思路其实不是难点,怎样操作数组才是需要考虑的。
------解决方案--------------------------------------------------------
128-bit整数转化为串,难度一般。
但是没说array1是小端格式还是大端格式。

------解决方案--------------------------------------------------------
其实这道题还是应该用除十取余法,因为这个方法非常奏效,算法简单易行,而且不易出错。问题的关键在于怎么对大数实现除十取余,显然用常规的除法是难以实现的,主要是寄存器位数不够。所以除十取余必须转化为移位运算和加减运算才行。除十取余问题要是解决了,这道题目也就解决了。
--------------------------------------------
f 0 f
a1 a2 a3
这就是高阶。
个位其实就是 15+0*6+6*15=105
10位就是0*1+5*15=75
100位2*15=30
30 00
75 0
105
------
3855
------解决方案--------------------------------------------------------
x86的FPU的FBSTP指令是不是能把FPU里的整数变成BCD数?
如果是的话那,128位的2进制,先用10亿除几次,取余,分成5个32位数,然后把它们一个一个按整形加载到FPU中,再以BCD格式取出来,再拼起来.
------解决方案--------------------------------------------------------
上面的方法中,被除数放在数组中,余数放在数组中,商放在被除数数组中,每次求得的商当作下一次使用的被除数,每次取得的余数加上30H后依次填入个位,十位……
这个思路应该是最好的办法
------解决方案--------------------------------------------------------
上面的程序还有点小错误,再次修正:

;假设array1是按字节小端排列的
;没有考虑array1全是0的情况
mov edi,array2
mov ecx,10
@next1:
xor ebx,ebx
xor edx,edx
mov esi,12
@next2:
mov eax,[array1+esi]
div ecx
or ebx,eax
mov [array1+esi],eax
sub esi,4
jns @next2
lea eax,[edx+48]
stosb
test ebx,ebx
jnz @next1
sub edi,array2+1
------解决方案--------------------------------------------------------
用C完成的对任意长度的16进制字符串,转10进制字符串。
#include <stdio.h>

static char *array1 = "ffffffffffffffff ";

int main()
{
char h[256];
  相关解决方案