所谓进制,就是逢几进一,r 进制就是逢 r 进一,就是一种计数方法。
例如
* 一分钟六十秒,逢六十进一,就是六十进制; * 一天二十四小时,逢二十四进一,就是二十四进制; * 一星期七天,逢七进一,就是七进制; * 一年十二个月,逢十二进一,就是十二进制; * 小学数学是逢十进一,就是十进制; * 而计算机中的数据只有 0 和 1,逢二进一,就是二进制。
注意
* 计算机只能识别二进制,人类最习惯使用的是十进制。 * 八进制数前面要加0(注意是数字零而不是字母 o),十六进制数前面要加0x或0X,而十进制前面什么都不加。
定义
十进制: 十进制为逢十进一,它只有 0、1、2、3、4、5、6、7、8、9 这十个基数。 逢十进一的意思就是: 9 再加 1 就变为 10,即向前进了一位,原来的 9 变成 0; 二进制: 二进制为逢二进一,它只有 0 和 1 两个基数。 逢二进一的意思就是: * 1 再加 1 就变成 10,即向前进了一位,原来的 1 变成 0; * 再加 1 就是 11; * 再加 1 又逢二,再往前进一位,进一位后第二个 1 又逢二再进位,就是 100 了; * 再加 1 变成 101,再加 1 变成 110,再加 1 变成 111,再加 1 变成 1000…… 八进制: 八进制就是逢八进一,它只有 0、1、2、3、4、5、6、7 这八个基数。 逢八进一的意思就是: * 7 再加 1 就变成 10,即向前进了一位,原来的 7 变成 0; * 11 再加 7 就变成了 20,即向前进了一位,原来的 1(11中的个位数) 变成 0; 十六进制: 十六进制就是逢十六进一,它有 0、1、2、3、4、5、6、7、8、9、A、B、C、D、E、F 这十六个基数。注意:字母不区分大小写 逢十六进一的意思就是: * f 再加 1 就变成 10,即向前进了一位,原来的 f 变成 0; * 11 再加 f 就变成了 20,即向前进了一位,原来的 1(11中的个位数) 变成 0; 总结: r 进制有 r 个基数,而且基数里面最大的是 r - 1,因为基数都是从 0 开始。 不同位数的值达到r时,就向前进1,原位数清0。 二进制: 十进制: 八进制: 十六进制: 0 1 =》1 0 1 = 1 0 1 = 1 0 1 = 1 1 1 =》 10 1 1 = 2 1 1 = 2 1 1 = 2 10 1 =》 11 2 1 = 3 2 1 = 3 2 1 = 3 11 1 =》 100 3 1 = 4 3 1 = 4 3 1 = 4 100 1 =》 101 4 1 = 5 4 1 = 5 4 1 = 5 101 1 =》 110 5 1 = 6 5 1 = 6 5 1 = 6 110 1 =》 111 6 1 = 7 6 1 = 7 6 1 = 7 111 1 =》 1000 7 1 = 8 7 1 = 10 7 1 = 8 1000 1 =》 1001 8 1 = 9 10 1 = 11 8 1 = 9 1001 1 =》 1010 9 1 = 10 11 1 = 12 9 1 = a 1010 1 =》 1011 10 1 = 11 12 1 = 13 a 1 = b 1011 1 =》 1100 11 1 = 12 13 1 = 14 b 1 = c 1100 1 =》 1101 12 1 = 13 14 1 = 15 c 1 = d 1101 1 =》 1110 13 1 = 14 15 1 = 16 d 1 = e 1110 1 =》 1111 14 1 = 15 16 1 = 17 e 1 = f 1111 1 =》 10000 15 1 = 16 17 1 = 20 f 1 = 10
M进制转换N进制的函数
r进制转换十进制:parseInt(str,radix) string :如果string不是字符串,它底层将通过使用 ToString 抽象操作 将其转成字符串 radix:范围在 [2,36]之间,表示当前 string 表示为几进制,在 radix 为 undefined,或者基数为 0 或者没有指定的情况下,JavaScript 作如下处理: * 如果字符串 string 以"0x"或者"0X"开头, 则基数是16 (16进制) * 如果字符串 string 以其它任何值开头,则基数是10 (十进制) * 其他永远都要明确给出radix参数的值 * 结果返回值为number类型 注意:如果第一个参数的第一个字符 跟 第二个参数的进制类型不相符,parseInt返回NaN。可以调用isNaN 来判断 parseInt 是否返回 NaN eg: parseInt('321',2) // NaN '321' 第一个字符非 0,1 这两个基数 eg: parseInt('321',37) // NaN radix 超过了区间[2,36] eg: isNaN(parseInt(0101,2)) // true (0101).toString() => 65 十进制转换r进制:(Number).toString(radix) Number:为一个十进制的数值,当然你也可以写一个16进制的数值,注意如果直接 radix:范围在 [2,36]之间,表示将 Number 转换成几进制,如果未指定 radix 参数,则默认值为 10; 如果 toString() 的 radix 参数不在 2 到 36 之间,将会抛出一个 RangeError。 为什么 2.toString(radix) 会报错呢? * 那是因为第一个点会被解析成小数点的点,如:2.0,后面的0省略了就是2.,因为2..toString(radix)才能正常执行。 * 所以正常写法都是(2).toString(radix) 最终JavaScript函数: function radixTransform(num,from,to){ num = typeof(num) === 'string' ? num : String(num) if ((from > 36 && from < 2) || (to > 36 && to < 2)) throw new Error('进制参数取值区间在[2,36]') let result = parseInt(num,from) if (typeof(result) === 'number' && isNaN(result)) throw new Error('转换值错误') return result.toString(to) }
进制之间的对应关系
二进制 |
八进制 |
十进制 |
十六进制 |
0 |
0 |
0 |
0 |
1 |
1 |
1 |
1 |
10 |
2 |
2 |
2 |
11 |
3 |
3 |
3 |
100 |
4 |
4 |
4 |
101 |
5 |
5 |
5 |
110 |
6 |
6 |
6 |
111 |
7 |
7 |
7 |
1000 |
10 |
8 |
8 |
1001 |
11 |
9 |
9 |
1010 |
12 |
10 |
a |
1011 |
13 |
11 |
b |
1100 |
14 |
12 |
c |
1101 |
15 |
13 |
d |
1110 |
16 |
14 |
e |
1111 |
17 |
15 |
f |
原因很简单,就是因为我们都有十个手指!进制的起源是用于记数的,人类刚开始都是用手指计数的。 即使是现在的小朋友算数也还是喜欢用手指,所以人类最习惯用十进制。
计算机为什么用的是二进制
因为二进制从硬件上比较容易实现。 任何事物最少也有两种不同的状态,所以区分成两种状态比较容易。 但是要将一个硬件硬生生地区分成十种不同的状态,这个就太难、太复杂了。