递归两个私房菜(包含十进制数转换为任意进制数)

第六章递归
题目二借鉴自:
https://blog.csdn.net/u011954296/article/details/51029600
一.题目分析
题目一:将非负十进制整数n转换成b进制。(其中b=2~16)
这道题目要求将十进制分别转化为二进制、八进制和十六进制。递归函数重视寻找递归体和递归的终止条件。
题目二:任何一个正整数都可以用2的幂次方表示。例如:
137=27+23+20。同时约定方次用括号来表示,即ab可表示为a(b)。由此可知,137可表示为: 2(7)+2(3)+2(0)。进一步:7=22+2+20(21用2表示)3=2+20。所以最后137可表示为:
2(2(2)+2+2(0))+2(2+2(0))+2(0)。
先将输入数据137按指数从大到小分为2(7)+2(3)+2(0),然后又将指数按上面同样的方法分为2(2)+2+2(0)、2+2(0)、0,就可分出137的最终结果2(2(2)+2+2(0))+2(2+2(0))+2(0)。非常明显,这道题应该运用递归思想。
二.算法构造
题目一:
递归方法:递归体为ds(s / 2),递归终止条件为s0。其中s为输入的十进制数字。s%x,x为想转换的进制。当s0时,return。此外的情况,执行递归体。在十进制转换为二进制、十进制和十六进制问题上采取同样的方法。注意在十进制装换为十六进制时,若是s % 16 > 9),则需要执行printf("%c", s % 16) - 10 + ‘A’);。这是由于十六进制中09可以用自身表示,而1015需要用‘A’~‘F’表示。
非递归方法:输入十进制数s,s==0时,结束。其他情况执行s/x(x为想转换的进制),且输出s%x,执行此操作的条件为s!=0。所以要借助于do~while()语句。
题目二:如果输入fun(137,0),则输出为2(7)+2(3)+2(0)。 这时,如果对7和3递归处理,则为满足题意的输出。void fun(int n, int r),其中n为操作数,r为递归深度。
三.程序实现
题目一:

#include<stdio.h>
#include<windows.h>
//递归实现十进制转换为二进制
int ds(int s)
{
	//s = s / 2;	//取模操作
	//printf("%d", s % 2);    //对/2获得的整数进行取余操作
	if (s == 0)	
	{
		return;	
	}
	else
	{
		ds(s / 2);	//递归体
		printf("%d", s % 2);    //对s取余操作

	}
}
int main()
{
	int d = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &d);
	ds(d);
		system("pause");
	return 0;
}
//递归实现十进制转换为八进制
int ds(int s)
{
	if (s==0)	
	{
		return ;
	}
	else
	{
		ds(s / 8);//取模操作
		printf("%d", s % 8);    //对s进行取余操作
	}
}
int main()
{
	int d = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &d);
	ds(d);
	system("pause");
	return 0;
}
//递归实现十进制转换为十六进制
int ds(int s)
{
	if (s == 0)
	{
		return;
	}
	else
	{
		ds(s / 16);	
		if (s % 16 > 9)
			//printf("%c", s % 16);
			printf("%c", (s % 16) - 10 + 'A');
		else
		
			printf("%d", s % 16);

		
		//printf("%d", s % 16);    

	}
}
int main()
{
	int d = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &d);
	ds(d);
	system("pause");
	return 0;
}
//非递归实现十进制转换为二进制
int main()
{
	int s = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &s);
	if (s == 0)
	{
		return;
	}
	else
	do{
		s = s / 2;
		printf("%d", s % 2);
	}while(s!=0);// 对s取余操作
	system("pause");
	return 0;
}
//非递归实现十进制转换为八进制
int main()
{
	int s = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &s);
	if (s == 0)
	{
		return;
	}
	else
		do {
			s = s / 8;
			printf("%d", s % 8);
		} while (s != 0);// 对s取余操作
		system("pause");
		return 0;
}
//非递归实现十进制转换为十六进制
int main()
{
	int s = 0;
	printf("请输入一个十进制数:");
	scanf_s("%d", &s);
	if (s == 0)
	{
		return;
	}
	else
		do{
			s = s / 16;
			if (s % 16 > 9)
				printf("%c", (s % 16) - 10 + 'A');
			else
				printf("%d", s % 16);  
		} while (s != 0);
		system("pause");
		return 0;
}

题目二:

void fun(int n, int r)
{
	//递归结束,最先输出,不带+号
	if (1 == n)
	{
		//将r表示成0和2
		switch (r)
		{
			//2^0,递归深度为0
		case 0: printf("2(0)");
			break;
			//2^1,递归深度为1
		case 1: printf("2");
			break;
			//2^2,递归深度为2
		case 2:printf("2(2)");
			break;
			//2^r,递归深度为r
		default:
			printf("2(");
			fun(r, 0);
			printf(")");
		}
	}
	else
	{
		//n除以二,递归深度加1
		fun(n / 2, r + 1);
		//如果模2有余数,则为2^r
		if (1 == n % 2)
		{
			//将r表示成0和2
			switch (r)
			{
				//2^0,递归深度为0
			case 0:printf("+2(0)");
				break;
				//2^1,递归深度为1
			case 1:printf("+2");
				break;
				//2^2,递归深度为2
			case 2:printf("+2(2)");
				break;
				//2^r,递归深度为r
			default:
				printf("+2(");
				fun(r, 0);
				printf(")");
			}
		}
	}
}
int main()
{
	fun(137, 0);
	system("pause");
	return 0;
}
此题借鉴自:
https://blog.csdn.net/u011954296/article/details/51029600

四.调用过程
题目一:
在这里插入图片描述
上图为十进制转换为二进制的调用过程,十进制转换为八进制和十进制转换为十六进制的过程与上图方法相同。
五.运行结果
题目一:
十进制转化为二进制:
在这里插入图片描述
十进制转换为八进制:
在这里插入图片描述
十进制转换为十六进制:
在这里插入图片描述
题目二:
在这里插入图片描述
六.经验总结
在接触到题目一时,首先应该了解到数制之间该如何转换的细节。然后构思递归实现的具体细节。涉及递归处理问题时,必须要将大问题转换为小问题,最重要的是寻找递归终止条件和构造递归体。“除2取余,逆序输出”是十进制转换为二进制数的思想核心,其它进制的转换同理。。非递归实现题目一时,思路不变,对程序稍作改动,并且借助于do~while()语句即可。对于题目二余力不足呐。

#include using namespace std; int main() { cout<<"06209527 朱**的作业!"<<endl; char arr[33],arr1[50]; //组arr用来保存用户输入的整形 int b=0; int base; //base用来保存用户欲转换进制 int len; //衡量arr的长度 double sum=0,a=0; //sum是用户输入的浮点大小 cout<<"请输入一个浮点型整的小部分"<>arr; len=strlen(arr); for(int i=0;i<len;i++) { a=arr[i]-'0'; for(int j=-1;j<i;j++) a=a/10; sum+=a; } cout<<"您输入的浮点型小是:"<<sum<<endl; cout<<"请输入你要转换进制(大于0,小于36!)"<>base; if(base36) { cout<<"输入错误!请重新输入!"<<endl; } int n=0; while(sum!=0&&n0) sum=sum-b; n++; } cout<<"转换后的小为:"<<endl; cout<<"0."; arr1[n]=0; len=strlen(arr1); for(i=0;i57) //9的ASCII码为57 { switch(arr1[i]) { case 58:cout<<"A";break; case 59:cout<<"B";break; case 60:cout<<"C";break; case 61:cout<<"D";break; case 62:cout<<"E";break; case 63:cout<<"F";break; case 64:cout<<"G";break; case 65:cout<<"H";break; case 66:cout<<"I";break; case 67:cout<<"J";break; case 68:cout<<"K";break; case 69:cout<<"L";break; case 70:cout<<"M";break; case 71:cout<<"N";break; case 72:cout<<"O";break; case 73:cout<<"P";break; case 74:cout<<"Q";break; case 75:cout<<"R";break; case 76:cout<<"S";break; case 77:cout<<"T";break; case 78:cout<<"U";break; case 79:cout<<"V";break; case 80:cout<<"W";break; case 81:cout<<"X";break; case 82:cout<<"Y";break; case 83:cout<<"Z";break; } } else cout<<arr1[i]; } return 0; }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值