题目描述
写出一个程序,接受一个十六进制的数,输出该数值的十进制表示。(多组同时输入 )
输入一个十六进制的数值字符串。
输出该数值的十进制字符串。
解题思路
u1s1,如果从解题的角度,这题目是真的简单,因为基本上我学过的三门语言(C,C++,Python)中都提供了从输入流中读取十六进制数的方法。
// C
scanf("%x", &num) ;
// C++
C++: cin >> hex >> num ;
// Python3
num = int(input(), 16)但是这里有一个问题就是说在C/C++中整数存在上限,即便是unsigned long型也最大只能表示2^64-1。因此对于输入的16进制数值字符串不应该直接转换为整型数,而应该考虑大数运算(题目并没有考虑)。
代码实现
现在先给出不考虑大整数的通用解法(C++):其他进制转10进制
首先给出数字到字符,和字符到数字的映射
// 两个全局数组
char Num2Char[] = "0123456789abcdefghijklmnopqrstuvwxyz" ;
// 数组Char2Num可以通过循环语句初始化
int Char2Num[127] = {
['0'] = 0, ['1'] = 1, ['2'] = 2, ['3'] = 3, ['4'] = 4, ['5'] = 5 ,
['6'] = 6, ['7'] = 7, ['8'] = 8, ['9'] = 9, ['a'] = 10, ['b'] = 11,
['c'] = 12, ['d'] = 13, ['e'] = 14, ['f'] = 15, ['g'] = 16, ['h'] = 17,
['i'] = 18, ['j'] = 19, ['k'] = 20, ['l'] = 21, ['m'] = 22, ['n'] = 23,
['o'] = 24, ['p'] = 25, ['q'] = 26, ['r'] = 27, ['s'] = 28, ['t'] = 29,
['u'] = 30, ['v'] = 31, ['w'] = 32, ['x'] = 33, ['y'] = 34, ['z'] = 35,
} ;对于其他进制转10进制,只需要将对应的位置的数字乘以相应的权值
int Other2Dec(string numstr, int base)
{
int sum = 0 ;
for(auto ch : numstr)
sum = (sum * base) + Char2Num[(int)ch] ;
return sum ;
}10进制转其他进制,可以通过不断对数字做除法实现。由于得到的余数序列是反序的,因此用栈实现。
string Dec2Other(int num, int base)
{
stack<int> st ;
while(num > 0){
st.push(num % base) ;
num = num / base ;
}
string re = "";
while(st.empty() != true){
re += Num2Char[st.top()] ;
st.pop() ;
}
return re ;
}如果要实现16进制数值字符串转10进制,只需要封装一下就好了
int Hex2Dec(string s)
{
// 如果串s中含前缀
s.erase(s.begin(), s.begin()+2) ;
return Other2Dec(s, 16) ;
}现在考虑大数,如果输入的16进制数超过了C++能够表示的整数范围,那么使用字符串表示十进制整数,字符串的每1位表示一个十进制位。
// 大数乘以整型数
string MUL(string s, int num)
{
reverse(s.begin(), s.end()) ;
int Carry = 0 ;
for(int i = 0; i < s.length(); i++){
int temp = Char2Num[(int)s[i]] * num + Carry ;
s[i] = Num2Char[temp % 10];
Carry = temp / 10 ;
}
cout << Carry << endl ;
while(Carry > 0){
s.push_back(Num2Char[Carry % 10]) ;
Carry /= 10 ;
}
reverse(s.begin(), s.end()) ;
return s ;
}
// 大数加整型数
string ADD(string s, int num)
{
reverse(s.begin(), s.end()) ;
int Carry = 0 ;
int i = 0 ;
int temp = Char2Num[(int)s[i]] + num ;
do{
if(i >= s.length()){
s.push_back(Num2Char[temp % 10]) ;
}else{
s[i] = Num2Char[temp % 10] ;
}
Carry = temp / 10 ;
temp = Char2Num[(int)s[++i]] + Carry ;
}while(Carry != 0) ;
reverse(s.begin(), s.end()) ;
return s ;
}
// 其他进制转10进制数
string Other2Dec(const string &hexstr, int base)
{
string sum ;
for(auto ch : hexstr)
sum = ADD(MUL(sum, base), Char2Num[int(ch)]) ;
return sum ;
}实际上只是更改了数据结构和对应的操作算法,框架是一样的,每个位置上的其他进制符号乘以对应的权值,最后计算和。算法的效率相对较低,因为1个字节只表示一个10进制位,可以vector<int>数据额类型,每一个4个字节的int类型(最大表示2^31-1)),可以表示10个10进制位。</int>

京公网安备 11010502036488号