目录
常用进制类型
计算机基础中,对于进制有进行介绍,这里再回顾一下。
二进制(binary):
在数学和数字电路中指以2为基数的记数系统,以2为基数代表系统是二进位制的。这一系统中,通常用两个不同的符号0(代表零)和1(代表一)来表示。
八进制(Octal):
一种以8为基数的计数法,采用0,1,2,3,4,5,6,7八个数字,逢八进1。一些编程语言中常常以数字0开始表明该数字是八进制。八进制的数和二进制数可以按位对应(八进制一位对应二进制三位),因此常应用在计算机语言中。
十进制(Decimal System):
每相邻的两个计数单位之间的进率都为十;十进制是中华民族的一项杰出创造,在世界数学史上有重要意义。著名的英国科学史学家李约瑟教授曾对中国商代记数法予以很高的评价,"如果没有这种十进制,就几乎不可能出现我们现在这个统一化的世界了",李约瑟说:"总的说来,商代的数字系统比同一时代的古巴比伦和古埃及更为先进更为科学。"
十六进制(Hexadecimal):
在数学中是一种逢16进1的进位制。一般用数字0到9和字母A到F(或a~f)表示,其中:A~F表示10~15。
进制转换
因为机器中使用二进制进行表示,但对于人来说,根本无法看懂,所以,必然存在一个进制转换的需要,通过一定的方法,将机器中的数据转换成人能够读懂的数据。
转换原则:
不同进制之间的转换本质就是确定各个不同权值位置上的数码。转换正整数的进制的有一个简单算法,就是通过用目标基数作长除法;余数给出从最低位开始的“数字”
基于上述原则详细解释十进制转换成二进制:
十进制整数部分转换:用2去除十进制整数,可以得到一个商和余数;再用2去除商,又会得到一个商和余数,如此进行,直到商为零时为止,然后把先得到的余数作为二进制数的低位有效位,后得到的余数作为二进制数的高位有效位,依次排列起来。
十进制小数部分转换:用2乘十进制小数,可以得到积,将积的整数部分取出,再用2乘余下的小数部分,又得到一个积,再将积的整数部分取出,如此进行,直到积中的小数部分为零,或者达到所要求的精度为止。
转换方法
十进制转二进制
1)把十进数除以2,记下余数(余数保存在字符串中),现用商除以2,再记下余数,如此循环,直到商为0。
2)把保存余数的字符串反过来,就是结果。
例如123转化成二进制:
123/2=61余1
61/2=30余1
30/2=15余0
15/2=7余1
7/2=3余1
3/2=1余1
1/1=0余1
结果是1101111,反过来就是1111011。
二进制转十进制
把二进制字符串从最高位(左边第一位)开始用商乘以2再加余数(该位的数字),如此循环,左边第一位的商肯定是0。
例如1111011转化成十进制:
0*2+1=1
1*2+1=3
3*2+1=7
7*2+1=15
15*2+0=30
30*2+1=61
61*2+1=123
结果是123。
/*
* 程序名:book.c,此程序演示十进制和二进制的互相转换。
* 作者:C语言技术网(www.freecplus.net) 日期:20190525。
*/
#include "stdio.h"
#include <string.h>
// 把十进制整数转换为二进制的字符串。
// dec:待转换的十进制整数。
// pbin:用于存放转换后的字符串的地址,注意,您必须保证pbin足以存放转换后的结果,否则可能会产生内存溢出。在64位操作系统中,long的最大取值为2的64次方,所以,pbin最大不必超过65。
void dectobin(const long dec,char *pbin)
{
long ys=0; // 余数。
int s=dec; // 商。
int ii=0; // 位数的计数器。
char result[65]; // 十进制转换成二进制后,保存在result中,再反过来存放到pbin中。
memset(result,0,sizeof(result));
// 把十进制转换为二进制,存放在result中。
while (s>0)
{
ys=s%2;
s=s/2;
result[ii]=ys+'0';
ii++;
}
// 再把result字符串反过来,存放在pbin中。
int jj=0;
for (;ii>0;ii--)
{
pbin[jj]=result[ii-1];
jj++;
}
pbin[jj]=0; // 出于安全的考虑,加上0表示字符串结束。
}
// 把二进制字符串转换为十进制。
// pbin:待转换的二进制字符串。
// 返回值:二进制字符串转换为十进制整数的结果。
long bintodec(const char *pbin)
{
int ii=0;
long result=0;
while (pbin[ii]!=0)
{
result=result*2+(pbin[ii]-'0');
ii++;
}
return result;
}
int main()
{
int ii=0;
printf("请输入一个整数:");
scanf("%d",&ii);
char str[65];
dectobin(ii,str); // 把十进制转换为二进制的字符串。
printf("%d的二进制输出是:%s\n",ii,str);
// 再把二进制字符串转换为十进制。
printf("%s转换为十进制的结果是:%d\n",str,bintodec(str));
}
同样的方法,我们也可以在其他进制之间进行转换。
二进制转十六进制
#include<stdio.h>
#include<string.h>
int main(){
int N,n,k,t,i,j,m;
char a[10005];
int b[10005]={0};
scanf("%d",&N);
while(N--){
scanf("%s",&a);
n=strlen(a);
for(i=0;i<n;i++)
b[i]=0;
k=0;
t=1;
m=0;
for(i=n-1;i>=0;i--){
b[k]+=(a[i]-'0')*t;
t*=2;
m++;
if(m%4==0){
k++;
t=1;
}
}
for(i=0;i<n;i++){
if(b[i]>=10){
switch(b[i]){
case 10 : b[i]='A'; break;
case 11 : b[i]='B'; break;
case 12 : b[i]='C'; break;
case 13 : b[i]='D'; break;
case 14 : b[i]='E'; break;
case 15 : b[i]='F'; break;
}
}
}
for(i=k;i>=0;i--){
if(b[i]!=0){
for(j=i;j>=0;j--){
if(b[j]>=65 && b[j]<=70 )
printf("%c",b[j]);
else printf("%d",b[j]);
}
break;
}
}
if(i==-1) printf("0");
printf("\n");
}
}
也可以使用下面的转换方法
#include <stdio.h>
#define BASE_SIZE 32
#define HEX 16
int binary_conversion( int value_t , int target_system_t )
{
int value = value_t;
int target_system = target_system_t;
int target_value [BASE_SIZE] = {0};
int target_value_i = 0;
while( value )
{
target_value[target_value_i] = value % target_system;
value = value / target_system;
target_value_i++;
}
if( target_system == HEX )
{
for( ; target_value_i >= 0; target_value_i-- )
{
printf( "%x", target_value[target_value_i] );
}
}else{
for( ; target_value_i >= 0; target_value_i-- )
{
printf( "%d", target_value[target_value_i] );
}
}
return 0;
}
int mian( void )
{
int input_value = 0;
int target_system = 0;
scanf( "%d,%d", &input_value, &target_system );
binary_conversion( input_value, target_system );
return 0;
}
浮点数计算问题
通过上面的进制转换,我们可以了解到基本的转换方法。而在我们平时变成的运算的时候,也经常会用到。
我们看到,在十进制转换到二进制的过程中,有时候是不能够完全精确的转换成一个二进制的数,比如0.1,转换成二进制就是0.000110011(0011无限循环),因为计算机中不可能存储无限的数据,超过一定位数后必然会丢失精度。
这时候,就必然存在着误差,也就是因为这个,导致了浮点数的计算问题。在编写代码的时候,经常会遇到这种问题。不过,只要我们在平时使用的时候多加注意,还是可以处理因为这个而带来的问题的。