目录
- 前言
- 进制转换
- 10进制转2进制
- 方法1
- 方法2
- 2进制转10进制
- 10进制转n进制
- n进制转10进制
- 2进制与8进制和16进制之间的快速转换
- 代码实现
- 10进制转n进制
- C++
- Python
- n进制转10进制
- C++
- Python
- 结尾
本文由Jzwalliser原创,发布在CSDN平台上,遵循CC 4.0 BY-SA协议。
因此,若需转载/引用本文,请注明作者并附原文链接,且禁止删除/修改本段文字。
违者必究,谢谢配合。
个人主页:blog.csdn.net/jzwalliser
前言
这一章,介绍一下不同的进制。
是否留意过,为什么经常能够看到一些以0x
开头的数字呢?
其实,这些数字都是16进制的。前缀0x
用于提示该数字为16进制。
一些其它的前缀还有二进制数0b
,八进制数0o
。
进制转换
如何转换进制呢?先来看看10进制转2进制吧。
10进制转2进制
方法1
概括来说,就是“余数倒序”法。每次都求出数字除以2的余数,再将数字除以二并删去小数直到数字为0;最后将这些余数倒过来。
例如,将 114514 114514 114514转换为2进制:
当前数字 | 算式 | 结果 | 余数 |
---|---|---|---|
114514 114514 114514 | 114514 ÷ 2 = 114514÷2= 114514÷2= | 57257 57257 57257 | 0 0 0 |
57257 57257 57257 | 57257 ÷ 2 = 57257÷2= 57257÷2= | 28628 28628 28628 | 1 1 1 |
28628 28628 28628 | 28628 ÷ 2 = 28628÷2= 28628÷2= | 14314 14314 14314 | 0 0 0 |
14314 14314 14314 | 14314 ÷ 2 = 14314÷2= 14314÷2= | 7157 7157 7157 | 0 0 0 |
7157 7157 7157 | 7157 ÷ 2 = 7157÷2= 7157÷2= | 3578 3578 3578 | 1 1 1 |
3578 3578 3578 | 3578 ÷ 2 = 3578÷2= 3578÷2= | 1789 1789 1789 | 0 0 0 |
1789 1789 1789 | 1789 ÷ 2 = 1789÷2= 1789÷2= | 894 894 894 | 1 1 1 |
894 894 894 | 894 ÷ 2 = 894÷2= 894÷2= | 447 447 447 | 0 0 0 |
447 447 447 | 447 ÷ 2 = 447÷2= 447÷2= | 223 223 223 | 1 1 1 |
223 223 223 | 223 ÷ 2 = 223÷2= 223÷2= | 111 111 111 | 1 1 1 |
111 111 111 | 111 ÷ 2 = 111÷2= 111÷2= | 55 55 55 | 1 1 1 |
55 55 55 | 55 ÷ 2 = 55÷2= 55÷2= | 27 27 27 | 1 1 1 |
27 27 27 | 27 ÷ 2 = 27÷2= 27÷2= | 13 13 13 | 1 1 1 |
13 13 13 | 13 ÷ 2 = 13÷2= 13÷2= | 6 6 6 | 1 1 1 |
6 6 6 | 6 ÷ 2 = 6÷2= 6÷2= | 3 3 3 | 0 0 0 |
3 3 3 | 3 ÷ 2 = 3÷2= 3÷2= | 1 1 1 | 1 1 1 |
1 1 1 | 1 ÷ 2 = 1÷2= 1÷2= | 0 0 0 | 1 1 1 |
最后,将余数倒过来: 11011111101010010 11011111101010010 11011111101010010。
所以, ( 114514 ) 10 = ( 11011111101010010 ) 2 (114514)_{10}=(11011111101010010)_2 (114514)10=(11011111101010010)2
方法2
概括来说,叫“2的幂次法”。不停地求2的幂,直到比需要转换的数字大。之后,逐个进行比较,大于记为 1 1 1,然后相减,小于记为 0 0 0。具体如下,还是 114514 114514 114514:
2 17 2^{17} 217 | 2 16 2^{16} 216 | 2 15 2^{15} 215 | 2 14 2^{14} 214 | 2 13 2^{13} 213 | 2 12 2^{12} 212 | 2 11 2^{11} 211 | 2 10 2^{10} 210 | 2 9 2^{9} 29 | 2 8 2^{8} 28 | 2 7 2^{7} 27 | 2 6 2^{6} 26 | 2 5 2^{5} 25 | 2 4 2^{4} 24 | 2 3 2^{3} 23 | 2 2 2^{2} 22 | 2 1 2^{1} 21 | 2 0 2^{0} 20 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
131072 131072 131072 | 65536 65536 65536 | 32768 32768 32768 | 16384 16384 16384 | 8192 8192 8192 | 4096 4096 4096 | 2048 2048 2048 | 1024 1024 1024 | 512 512 512 | 256 256 256 | 128 128 128 | 64 64 64 | 32 32 32 | 16 16 16 | 8 8 8 | 4 4 4 | 2 2 2 | 1 1 1 |
过程:
当前数字 | 比较算式 | 结果 | 算式 |
---|---|---|---|
114514 114514 114514 | 114514 ≥ 131072 114514\geq131072 114514≥131072 | False(0) | / |
114514 114514 114514 | 114514 ≥ 65536 114514\geq65536 114514≥65536 | True(1) | 114514 − 65536 = 48978 114514-65536=48978 114514−65536=48978 |
48978 48978 48978 | 48978 ≥ 32768 48978\geq32768 48978≥32768 | True(1) | 48978 − 32768 = 16210 48978-32768=16210 48978−32768=16210 |
16210 16210 16210 | 16210 ≥ 16384 16210\geq16384 16210≥16384 | False(0) | / |
16210 16210 16210 | 16210 ≥ 8192 16210\geq8192 16210≥8192 | True(1) | 16210 − 8192 = 8018 16210-8192=8018 16210−8192=8018 |
8018 8018 8018 | 8018 ≥ 4096 8018\geq4096 8018≥4096 | True(1) | 8018 − 40963922 8018-4096 3922 8018−40963922 |
3922 3922 3922 | 3922 ≥ 2048 3922\geq2048 3922≥2048 | True(1) | 3922 − 20481847 3922-2048 1847 3922−20481847 |
1847 1847 1847 | 1847 ≥ 1024 1847\geq1024 1847≥1024 | True(1) | 1847 − 1024 = 850 1847-1024=850 1847−1024=850 |
850 850 850 | 850 ≥ 512 850\geq512 850≥512 | True(1) | 850 − 512 = 338 850-512=338 850−512=338 |
338 338 338 | 338 ≥ 256 338\geq256 338≥256 | True(1) | 228 − 256 = 82 228-256=82 228−256=82 |
82 82 82 | 82 ≥ 128 82\geq128 82≥128 | False(0) | / |
82 82 82 | 82 ≥ 64 82\geq64 82≥64 | True(1) | 82 − 64 = 18 82-64=18 82−64=18 |
18 18 18 | 18 ≥ 32 18\geq32 18≥32 | False(0) | / |
18 18 18 | 18 ≥ 16 18\geq16 18≥16 | True(1) | 18 − 16 = 2 18-16=2 18−16=2 |
2 2 2 | 2 ≥ 8 2\geq8 2≥8 | False(0) | / |
2 2 2 | 2 ≥ 4 2\geq4 2≥4 | False(0) | / |
2 2 2 | 2 ≥ 2 2\geq2 2≥2 | True(1) | 2 − 2 = 0 2-2=0 2−2=0 |
0 0 0 | 0 ≥ 1 0\geq1 0≥1 | False(0) | / |
若将False记为 0 0 0,将True记为 1 1 1,那么将所有的比较结果从上往下排一遍,就得到了 011011111101010010 011011111101010010 011011111101010010。即, ( 114514 ) 10 = ( 11011111101010010 ) 2 (114514)_{10}=(11011111101010010)_2 (114514)10=(11011111101010010)2
2进制转10进制
假设有一个二进制数: ( 10110101 ) 2 (10110101)_2 (10110101)2,那么它的十进制是多少呢?
依然列出刚才的“幂次表”,将该二进制数填进去:
2 7 2^{7} 27 | 2 6 2^{6} 26 | 2 5 2^{5} 25 | 2 4 2^{4} 24 | 2 3 2^{3} 23 | 2 2 2^{2} 22 | 2 1 2^{1} 21 | 2 0 2^{0} 20 |
---|---|---|---|---|---|---|---|
128 128 128 | 64 64 64 | 32 32 32 | 16 16 16 | 8 8 8 | 4 4 4 | 2 2 2 | 1 1 1 |
1 1 1 | 0 0 0 | 1 1 1 | 1 1 1 | 0 0 0 | 1 1 1 | 0 0 0 | 1 1 1 |
然后,观察二进制数:如果当前位是1,那么就将上面的幂次加起来。
2 7 + 2 5 + 2 4 + 2 2 + 2 0 \space\space\space\space2^7+2^5+2^4+2^2+2^0 27+25+24+22+20
= 128 + 32 + 16 + 4 + 1 =128+32+16+4+1 =128+32+16+4+1
= 181 =181 =181
所以, ( 10110101 ) 2 = ( 181 ) 10 (10110101)_2=(181)_{10} (10110101)2=(181)10
10进制转n进制
其实方法和前面介绍的“余数倒序”法大同小异。直接上例子:将 ( 1919 ) 10 (1919)_{10} (1919)10转换为 16 16 16进制。
当前数字 | 算式 | 结果 | 余数 |
---|---|---|---|
1919 1919 1919 | 1919 ÷ 16 = 1919÷16= 1919÷16= | 119 119 119 | 15 15 15 |
119 119 119 | 119 ÷ 16 = 119÷16= 119÷16= | 7 7 7 | 7 7 7 |
7 7 7 | 7 ÷ 16 = 7÷16= 7÷16= | 0 0 0 | 7 7 7 |
再按照16进制的规则,10进制下的二位数分别对应16进制下的一位数:
10进制 | 16进制 |
---|---|
10 10 10 | A A A |
11 11 11 | B B B |
12 12 12 | C C C |
13 13 13 | D D D |
14 14 14 | E E E |
15 15 15 | F F F |
将余数倒序过来后,是 77 F 77F 77F。
所以 ( 1919 ) 10 = ( 77 F ) 16 (1919)_{10}=(77F)_{16} (1919)10=(77F)16
n进制转10进制
和前面写的“幂次表”法相类似,由当前位乘幂次。
例:16进制数 ( 810 A ) 16 (810A)_{16} (810A)16转换为十进制是多少?
1 6 3 16^3 163 | 1 6 2 16^2 162 | 1 6 1 16^1 161 | 1 6 0 16^0 160 |
---|---|---|---|
4096 4096 4096 | 256 256 256 | 16 16 16 | 1 1 1 |
8 8 8 | 1 1 1 | 0 0 0 | A A A |
10 × 1 6 0 + 0 × 1 6 1 + 1 × 1 6 2 + 8 × 1 6 3 \space\space\space\space10\times16^0+0\times16^1+1\times16^2+8\times16^3 10×160+0×161+1×162+8×163
= 10 × 1 + 0 × 16 + 1 × 256 + 8 × 4096 =10\times1+0\times16+1\times256+8\times4096 =10×1+0×16+1×256+8×4096
= 33034 =33034 =33034
所以 ( 810 A ) 16 = ( 33034 ) 10 (810A)_{16}=(33034)_{10} (810A)16=(33034)10。
2进制与8进制和16进制之间的快速转换
由于 8 = 2 3 , 16 = 2 4 8=2^3,16=2^4 8=23,16=24,它们之间存在倍数关系,所以2进制转换为8进制和16进制有一种快捷的方法。
现在,列出对应的表:
16进制 | 8进制 | 2进制 | 10进制 |
---|---|---|---|
0 0 0 | 0 0 0 | 0 0 0 | 0 0 0 |
1 1 1 | 1 1 1 | 1 1 1 | 1 1 1 |
2 2 2 | 2 2 2 | 10 10 10 | 2 2 2 |
3 3 3 | 3 3 3 | 11 11 11 | 3 3 3 |
4 4 4 | 4 4 4 | 100 100 100 | 4 4 4 |
5 5 5 | 5 5 5 | 101 101 101 | 5 5 5 |
6 6 6 | 6 6 6 | 110 110 110 | 6 6 6 |
7 7 7 | 7 7 7 | 111 111 111 | 7 7 7 |
8 8 8 | 10 10 10 | 1000 1000 1000 | 8 8 8 |
9 9 9 | 11 11 11 | 1001 1001 1001 | 9 9 9 |
A A A | 12 12 12 | 1010 1010 1010 | 10 10 10 |
B B B | 13 13 13 | 1011 1011 1011 | 11 11 11 |
C C C | 14 14 14 | 1100 1100 1100 | 12 12 12 |
D D D | 15 15 15 | 1101 1101 1101 | 13 13 13 |
E E E | 16 16 16 | 1110 1110 1110 | 14 14 14 |
F F F | 17 17 17 | 1111 1111 1111 | 15 15 15 |
将16进制转换位2进制时,将每一位16进制替换为4位对应的2进制;若是8进制则替换为3位。
举个例子:
16进制数 ( A C F 4561 ) 16 (ACF4561)_{16} (ACF4561)16的二进制是什么?
A | C | F | 4 | 5 | 6 | 1 |
---|---|---|---|---|---|---|
1010 | 1100 | 1111 | 0100 | 0101 | 0110 | 0111 |
所以 ( A C F 4561 ) 16 = ( 1010110011110100010101100111 ) 2 (ACF4561)_{16}=(1010110011110100010101100111)_2 (ACF4561)16=(1010110011110100010101100111)2。
再举个例子:8进制数 ( 6257134 ) 8 (6257134)_8 (6257134)8的二进制是什么?
6 | 5 | 2 | 7 | 1 | 3 | 4 |
---|---|---|---|---|---|---|
110 | 101 | 010 | 111 | 001 | 011 | 100 |
所以 ( 6257134 ) 8 = ( 110101010111001011100 ) 2 (6257134)_8=(110101010111001011100)_2 (6257134)8=(110101010111001011100)2。
而2进制转换为8进制、16进制也是如此:每3个或4个2进制位(bit)分成一组,然后替换为对应的8进制或16进制数。
如: ( 1001011 ) 2 (1001011)_2 (1001011)2转换为16进制为多少?
0100 | 1011 |
---|---|
4 | B |
所以 ( 1001011 ) 2 (1001011)_2 (1001011)2= ( 4 B ) 16 (4B)_{16} (4B)16。
代码实现
10进制转n进制
C++
string dec_to_m(int n,int m){ //十进制数n转m进制string digit = "0123456789ABCDEF"; //位数if(n == 0){ //如果除完了return "";}return dec_to_m(n / m,m) + digit[n % m]; //依次相除并添加位数
}
Python
def dec_to_m(n,m): #十进制数n转m进制digit = "0123456789ABCDEF" #位数if n == 0: #如果除完了return ""return dec_to_m(int(n / m),m) + digit[n % m] #依次相除并添加位数
n进制转10进制
C++
long long int n_to_dec(string m,int base){ //base进制的数字mreverse(m.begin(),m.end()); //将数字反转过来,方便遍历long long int ans = 0; //十进制的数for(int i = 0;i < m.size();i++){ //遍历每一位int digit; //当前位if('0' <= m[i] and m[i] <= '9'){ //将字符转换为整数digit = m[i] - '0';}else if('A' <= m[i] and m[i] <= 'Z'){ //如果是16进制则需要处理字母digit = m[i] - 'A' + 10;}else if('a' <= m[i] and m[i] <= 'z'){ //如果是16进制则需要处理字母digit = m[i] - 'a' + 10;}ans += pow(base,i) * digit; //依次累加}return ans;
}
Python
其实python可以直接作转换,只要int(number,base)
即可。不过这里还是完整写一遍进制转换以方便读者理解。
def n_to_dec(m,base): #base进制的数字mm = m[::-1] #将数字反转过来,方便遍历ans = 0 #十进制的数for i in range(len(m)): #遍历每一位digit = 0 #当前位if ord('0') <= ord(m[i]) <= ord('9'): #将字符转换为整数digit = ord(m[i]) - ord('0')elif ord('A') <= ord(m[i]) <= ord('Z'): #如果是16进制则需要处理字母digit = ord(m[i]) - ord('A') + 10elif ord('a') <= ord(m[i]) <= ord('z'): #如果是16进制则需要处理字母digit = ord(m[i]) - ord('a') + 10ans += base ** i * digit #依次累加return ans
结尾
感谢您的阅读!点个赞再走哦~
还有,祝大家万事如意!