5进制转换文档格式.docx
- 文档编号:19770715
- 上传时间:2023-01-10
- 格式:DOCX
- 页数:22
- 大小:26.72KB
5进制转换文档格式.docx
《5进制转换文档格式.docx》由会员分享,可在线阅读,更多相关《5进制转换文档格式.docx(22页珍藏版)》请在冰豆网上搜索。
十六进制是人们在计算机指令代码和数据的书写中经常使用的数制。
在十六进制中,由十六个字符0~9以及A,B,C,D,E,F(或a,b,…,f)组成(它们分别表示十进制数10~15)来描述。
计数规则是逢十六进一,即基数R=16=24,通常在表示时用尾部标志H或下标16以示区别。
十六进制数4AC8可写成(4AC8)16,或写成4AC8H。
6.六十进位制数(Sexagesimal)
古代人由于生产劳动的需要,要研究天文和历法,就牵涉到时间和角度了。
因为历法需要的精确度较高,时间的单位小时,角度的单位度都嫌太大。
必须进一步研究他们的小数。
它们的小数都具有这样的性质:
使1/2,1/3,1/4,1/5,1/6等都能成为他的整数倍。
以1/60作为单位,就正好具有这个性质。
譬如:
1/2等于30个1/60,1/3等于20个1/60,1/4等于15个1/60……这种小数的进位制在表示有些数时很方便。
例如常遇到的1/3,在十进位制中要变成无限小数,但在这种进位制中就是一个整数。
因此就出现了六十进制。
5.1.3进制转换
在实际运算中,我们经常用到各种不同的进制,这就需要在各种数制之间进行转换。
1.其他进制转换为十进制(按权求和)
方法是:
将其它进制按权位展开,然后各项相加,就得到相应的十进制数。
例1:
N=(10110.101)B=(?
)D
按权展开N=1*24+0*23+1*22+1*21+0*20+1*2-1+0*2-2+1*2-3
=16+4+2+0.5+0.125=(22.625)D
例2:
(38A.11)16转换为十进制数
(38A.11)16
=3×
162+8×
161+10×
160+1×
16-1+1×
16-2
=768+128+10+0.0625+0.0039
=906.0664
2.十进制转换成其它进制
分两部分分别进行的,即整数部分和小数部分。
(1)整数部分:
(基数除法)
把我们要转换的数除以新的进制的基数,把余数作为新进制的最低位;
把上一次得到的商再除以新的进制基数,把余数作为新进制的次低位;
继续上一步,直到最后的商为零,这时的余数就是新进制的最高位。
(2)小数部分:
(基数乘法)
把要转换数的小数部分乘以新进制的基数,把得到的整数部分作为新进制小数部分的最高位。
把上一步得的小数部分再乘以新进制的基数,把整数部分作为新进制小数部分的次高位;
继续上一步,直到小数部分变成零为止。
或者达到预定的精度要求或位数要求也可以。
3.二进制与八进制、十六进制的相互转换
二进制转换为八进制、十六进制:
它们之间满足23和24的关系,因此把要转换的二进制从低位到高位每3位或4位一组,高位不足时在有效位前面添“0”,然后把每组二进制数转换成八进制或十六进制即可。
八进制、十六进制转换为二进制时,把上面的过程逆过来即可。
也就是把一个八或十六进制位转换为3或4个二进制位。
例3:
N=(C1B)H=(?
)B
(C1B)H=1100/0001/1011=(110000011011)B
4.数制转换的一般化
(1)R进制转换成十进制
任意R进制数按权展开,相加即可得十进制数据。
N=1101.0101B=1*23+1*22+0*21+1*20+0*2-1+1*2-2+0*2-3+1*2-4=8+4+0+1+0+0.25+0+0.0625=13.3125
N=5A.8H=5*161+A*160+8*16-1=80+10+0.5=90.5
(2)十进制转换R进制
十进制数转换成R进制数,须将整数部分和小数部分分别转换。
整数转换——除R取余法,规则:
1用R去除给定的十进制数的整数部分,取其余数作为转换后的R进制数据的整数部分最低位数字;
②再用R去除所得的商,取其余数作为转换后的R进制数据的高一位数字;
③重复执行②操作,直到商为0结束。
小数转换——乘R取整法,规则:
1用R去乘给定的十进制数的小数部分,取乘积的整数部分作为转换后R进制小数点后第一位数字;
②再用R去乘上一步乘积的小数部分,然后取新乘积的整数部分作为转换后R进制小数的低一位数字;
2重复②操作,一直到乘积为0,或已达到精度要求或位数要求为止。
解决数制转换问题时,如果所给的数值不是用十进制表示的,一般用一个字符型数组来存放。
数组的每个元素分别存储它的一位数字。
然后按位转换求和,得到十进制表示;
再把十进制表示转换成所求的数制表示。
转换的结果也用一个字符型数组表示,每个元素表示转换结果的一位数字。
根据数制表示中相邻位的基数关系,可以把不同的数制分成两类。
一类数制表示中,相邻位的基数是等比关系,例如我们熟悉的十进制表示。
另一类数制表示中,相邻位的基数是不等比的。
例如在时间表示中,从秒到分采用60进进制;
从月到年则采用12进制。
把一个数值从数制B的表示bmbm-1bm-2...b1转换成十进制表示dndn-1dn-2...d1比较简单。
假设数制B中,第i位的基数为basei(1<
=i<
=m),直接把basei与bi相乘,然后对全部乘积求和。
从十进制表示dndn-1dn-2...d1到bmbm-1bm-2...b1的转换需要分两种情况考虑:
●数制B中相邻数字的基数是等比关系,即:
basei(1<
=m)可以表示成Ci-1,其中C是一个常量。
将dndn-1dn-2...d1除以C,余数即为b1;
将dndn-1dn-2...d1和C相除的结果再除以C,余数即为b2;
…;
直至计算出为bm止。
●数制B中相邻数字的基数不等比。
需要先判断dndn-1dn-2...d1在数制B中需要的位数m,然后从高位到低位依次计算bm、bm-1、bm-2、...、b1。
5.2例5001特殊的四位数
(来源:
2405/poj.org2196)
问题描述:
找出并输出所有的4位数(十进制数)中具有如下属性的数:
四位数字之和等于其十六进制形式各位数字之和,也等于其十二进制形式各位数字之和。
例如:
十进制数2991,其四位数字之和2+9+9+1=21。
由于2991=1*1728+8*144+9*12+3,其十二进制形式为1893(12),其各位数字之和也为21。
但是它的十六进制形式为BAF(16),其各位数字之和等于11+10+15=36。
因此你的程序要舍去2991这个数据。
下一个数2992,其十进制、十二进制、十六进制形式各位数字之和均为22,因此2992符合要求,应该输出来。
(只考虑4位数,2992是第一个符合要求的数)
输入:
本题没有输入。
输出:
你的程序要求输出2992及其他更大的、满足要求的四位数(要求严格按升序输出),每个数占一行(前后都没有空行),整个输出以换行符结尾。
输出中没有空行。
输出中的前几行如输出样例所示。
输入样例:
输出样例:
2992
2993
2994
2995
2996
2997
2998
2999
...
解题分析:
该题在求解时要用到枚举的算法思想,即枚举所有的四位数(1000-9999),判断其是否满足十六进制、十二进制和十进制形式的各位数之和相等。
由于题目已经告诉你3000以内的所有满足条件的数,因此我们可以直接输出这些数,从3000开始枚举。
将一个十进制数N转换到B进制,其方法是:
将N除以B取余数,直到商为0为止,存储得到的余数,然后逆序输出余数即可得到B进制下的数,但由于此题只需要得到N在16、12和10进制下各位的和,所以不需要对余数逆序,直接累加其余数即可。
参考程序(zzg):
#include<
stdio.h>
stdlib.h>
string.h>
intbase(intb,intn)
{
intsum=0;
while(n!
=0)
{
sum+=n%b;
n/=b;
}
returnsum;
}
intmain()
inti,a;
printf("
2992\n2993\n2994\n2995\n2996\n2997\n2998\n2999\n"
);
for(i=3000;
i<
10000;
i++)
a=base(12,i);
if(base(10,i)==a&
&
a==base(16,i))
{
printf("
%d\n"
i);
}
return0;
5.3例5002进制转换
2031)
输入一个十进制数N,将它转换成R进制数输出。
输入数据包含多个测试实例,每个测试实例包含两个整数N(32位整数)和R(2<
=R<
=16,R<
>
10)。
为每个测试实例输出转换后的数,每个输出占一行。
如果R大于10,则对应的数字规则参考16进制(比如,10用A表示,等等)。
72
2312
-43
111
1B
-11
这题就是考察十进制转换为其他进制的用法,由于需要转换的是整数,因此只需要把十进制整数除以R取余即可。
这里可以采用循环或递归来实现即可。
由于R不确定,因此我们可以编写个函数来实现十进制转换为R进制的功能。
参考程序(hxx):
intTenToR(intnum,intr)
charm;
if(num==0)
return0;
TenToR(num/r,r);
m=(num%r>
9?
num%r-10+'
A'
:
num%r+'
0'
%c"
m);
}
intn,r;
while(scanf("
%d%d"
&
n,&
r)!
=EOF)
if(!
n)
0"
elseif(n>
0)
TenToR(n,r);
else
printf("
-"
TenToR(-n,r);
\n"
return0;
5.4例5003skew数
2973)
在skew二进制数表示中,第k位的值xk表示xk*(2k+1-1)。
每个位上的可能数字是0或1,最后面一个非零位可以是2,例如,10120(skew)=1*(25-1)+0*(24-1)+1*(23-1)+2*(22-1)+0*(21-1)=31+0+7+6+0=44.前十个skew数是0、1、2、10、11、12、20、100、101以及102。
输入包含一行或多行,每行包含一个整数n。
如果n=0表示输入结束,否则n是一个skew数。
对于每一个输入,输出它的十进制表示。
转换成十进制后,n不超过231-1=2147483647。
10120
200000000000000000000000000000
10
1000000000000000000000000000000
11
100
11111000001110000101101102000
44
2147483646
3
2147483647
4
7
1041110737
解题分析1:
由于n不超过231-1,因此可以直接用int类型来保存n,位权可以采用移位来实现。
参考程序1(hsl):
intmain(){
charstr[1010];
%s"
str)!
=EOF){
if(strcmp(str,"
)==0)break;
intl=strlen(str);
inti,j,ans=0,t1=1,t2;
for(i=l-1;
i>
=0;
i--){
t1=t1<
<
1;
t2=t1-1;
ans+=(str[i]-'
)*t2;
}
ans);
解题分析2:
由于skew数位数比较多,超过了int的范围,因此我们只能采用字符数组的形式来接收输入。
这里,最大的skew二进制数对应到十进制数为231-1=2147483647,对应的skew数为:
1000000000000000000000000000000。
一共31位,因此采用长度为32的字符数组即可。
剩下的工作就是按位权展开求和就能得到想要的结果。
参考程序2:
math.h>
charstr[32];
//读入的每个skew二进制数
intlen=strlen(str);
intnum=0;
//对应的十进制数
if(len==1&
str[0]=='
)break;
intweight=2;
//每位的权值为weight-1
inti;
for(i=len-1;
i--)
num+=(str[i]-'
)*(weight-1);
weight*=2;
num);
5.5例5004周易
2989)
有人说,中国古代的“周易”是二进制系统的起源,在该系统中,他们用“--”表示1,“---”表示0。
因此,二进制数字“011010”可以表述为“---\n--\n--\n---\n--\n---\n”(符号“\n”表示换行)。
现在的问题是如何把一个十进制数转换为“周易”中的二进制?
文件中包含多组测试数据。
每个测试数据占一行,包括一十进制整数n(0<
=n<
=1000000)和表示二进制位数的k(0<
k<
=20且n<
2^k)。
n=0,k=0表示输入结束。
对于每组测试数据,输出“周易”中对应的k行二进制数。
每组测试数据之间输出一个空行。
73
03
266
00
--
---
这题首先要把十进制数转换为二进制数,这个可以采用除2取余,再逆序输出即可。
其次就是如何输出k位,这里可能涉及到两种情况,一是k要大于实际二进制数的位数,那么前面需要用0来填补。
二是k小于实际的位数,那么需要在输出时控制只输出前k位(这里不会出现这种情况,因为题目中已经明确了n<
由于k>
0且k<
=20,因此我们可以使用一个20位长的整数数组来存储转换后的二进制数,初始化时全部为0。
#include<
inta[20];
intn,k;
inti;
while
(1)
scanf("
k);
if(n==0&
k==0)
break;
for(i=0;
i<
20;
i++)
a[i]=0;
i=0;
while(n)
a[i++]=n%2;
n=n/2;
for(i=k-1;
if(a[i]==1)
printf("
--\n"
else
---\n"
5.6例5005奶牛计算器
poj.org3191)
由于缺乏数学经验,奶牛想建立一个计算机器(它被称为Cowmpouter),使用二进制数字(基数为2),但它是建立在-2的基础上。
他们非常高兴,因为在-2进制表示的数字中不需要符号位。
你知道基数的权值都是从1开始的(0位),然后从右到左依次为基数1次方,基数2次方等等。
在-2进制中,其权值从右到左,依次为1,-2,4,-8,16,-32,…。
因此,从1计数依次是:
1,110,111,100,101,11010,11011,11000,11001等等。
很怪异的是,负数也那个用1和0表示,但没有符号位。
从-1向下计数依次为:
11,10,1101,1100,1111等等。
请帮助奶牛把普通的十进制整数(范围为:
-2,000,000,000到2,000,000,000)转换为-2进制对应的数。
输入只有一行,一个需要转换为-2进制的十进制整数。
对应的-2进制的数,没有前导0,0就表示0本身,只用1个0。
-13
110111
此题的解法基于以下几点:
(1)如果一个数是奇数,那么它的二进制形式的最后一位肯定是1,我们可以去掉此1,就是(x-1)/-2,进入
(2)。
(2)如果一个数的最后一位为0,我们可以把这个数右移(可以类比以2为基的二进制数的操作)一位,然后它的二进制的倒数第二个数就成了最后一个,就是x=x/-2,然后进入
(1)迭代,直到变为0。
intvalue;
charcache[100];
intcnt;
voidreverse()
chartmp;
for(i=0;
cnt/2;
tmp=cache[cnt-i-1];
cache[cnt-i-1]=cache[i];
cache[i]=tmp;
scanf("
%d"
value);
if(value==0)
gotoend;
while(value!
=1)
if(abs(value)%2!
=0)
cache[cnt++]='
1'
;
value=(value-1)/(-2);
else
value=value/(-2);
reverse();
cache[cnt]='
\0'
1%s"
cache);
end:
5.7例5006计算器设计
poj.org1546/1334)
ReallyNeato计算器公司最近邀请你的团队为他们设计一款超级Neato一代计算器。
作为计算机科学家,你建议该计算器能够在各种进制之间进行转换。
他们认为这是一个很好的想法,并要求你的团队先给出实现进制转换的算法原型。
公司经理告诉你,该计算器应该具有以下一些特征:
(1)可以显示7位;
(2)按键除了数字0到9外,还包括大写字母A到F;
(3)支持2~16进制。
输入文件中的每行为一个进制转换,包括3个数,第1个数是原进制下的一个整数,第2个数就是原进制,第3个数是转换后的进制。
这3个数的两边可能有一个或多个空格。
输入数据一直到文件结尾。
实现所有的进制转换,转换后的数右对齐到7位显示。
如果转换后的数的位数太多,超过7位,则输出“ERROR”,也是右对齐到。
1111000210
1111000216
2102101310
2102101315
1231242
1A152
12345671016
ABCD1615
120
78
1765
7CA
ERROR
11001
12D687
D071
longb2ten(char*x,in
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 转换
![提示](https://static.bdocx.com/images/bang_tan.gif)