C Primer Plus (第六版)课后编程练习答案2.12

C Primer Plus(第六版) 课后编程练习答案 2.12

(下面的所有代码是在Dev-c++环境下写的。)
第一题:这里只写了简单题,算是一个测试。
这道题目是很简单的入门题,题目要求多次调用printf函数进行标准输出,因为是复习,所以我使用了puts()函数进行实现。下面是代码:

#include<stdio.h>

int main(void)
{
	printf("Xu Dafeng\n");                //第一次调用printf函数
	printf("Xu\nDafeng\n");               //第二次调用
	puts("Xu dafeng");                    //这里是puts() ,由于put自带会在输出最后加一个换行符,所以无需加\n 
	fputs("Xu dafeng",stdout);            //fputs()不会在最后加一个换行符 
	printf("\n");
	return 0;
} 

fputs()函数一般和fgets()一起使用,fputs()的第二个参数是输出位置,如果打算输出到显示器的话,应该写stdout。fgets()函数的第二个参数是输入的长度,第三个参数是输入的位置。(从显示器读入是stdin)。
当然,其实你可以通过自定义来设计适合你的输入/输出函数。
如果你是初学者的话,对于这个程序你需要注意的是在开头应该加上:

#include<stdio.h>

虽然有些软件在没有这个头文件的情况下也能运行,但是最好加上。
stdio.h包含了printf和scanf的函数原型,也包含了很多的输入输出函数的函数原型。
int 表示定义的变量是整型变量。

第二题:
这里使用了一个交互的模式。

#include<stdio.h>

#define SIZE 20
#define LONG 100
int main(void)
{
	char name[SIZE],where[LONG];
	printf("请输入你的名字:\n");
	scanf("%s%*c",name);                   //这时一个输入函数,从用户键入的数据读取。特别关注这个换行符。 
	printf("现在请你输入你的籍贯:\n");
	gets(where);                          //这里无需加换行符,是因为gets会把换行符一起读取了。 
	printf("你的名字是:"); 
	puts(name);                           
	printf("你的籍贯是:%s\n",where);
	getchar();                             //这是为了让程序不会闪一下就结束,保证了缓冲时间,不是必要的。 
	return 0;
} 

在这里说明由于scanf()在这个程序里读取的是字符型常量(之所以说在这个程序里读取的是字符型常量,是因为在这里面%s转换说明是读取字符串),\n也是一个字符型常量,而%s会读取到空白符前,但是用户在发送输入的数据的时候会把\n(即回车键)一起发送给scanf一起读取,(也就是说,如果你输入的是“小明”然后点击了回车键以键入数据,这个时候缓冲区的数据是“小明\n”)
在这里结合%s的转换说明,读取完空白符前面的数据后,缓冲区还剩下\n,而换行符也是一个字符型常量,所以在第二个读取函数gets会读取\n,在输出的时候会再次输出\n,表示出来的是换行效果,这样就无法读取用户的地址,从而使程序无法达到我们的设计目的。这时可以用%*c来把\n读走,但是不赋给任何变量,也就是抛弃了\n这个字符常量。
输出如图
这里还有缓冲区这个概念没有解释清楚,由于这个概念较为复杂,可以先记着,后续会解释。

第三题
这题要编写一个程序把你的年龄换算成天数,题目说不考虑闰年,但是我们为了提高难度,在这里要考虑闰年问题。
分析如下:
1.首先我们要得到需要处理的数据,首先是你的出生日期,是三个整型变量,然后是今天的日期,也是三个整型变量。
2.然后我们要知道什么是闰年,闰年是能被400整除。或者能被4整除但不能被100整除的年份。
3.这里采用的算法是先计算从出生日期到今天一共经过几年,不满一年的部分先留着,也就是说,假如我2000.5.3出生,今天是2019.3.14,保留到2018.5.3,这里用伪代码说明也就是:
如果你今年已经过了生日,那么计算方法是(2019-2000)*365+今天的时间扣去你出生的日期(月份和日期)。
4.这里还没有考虑闰年问题,先计算你出生那天是不是闰年,如果不是的话,找到往后最近的闰年,然后+4直到到达今年的日期,有几个闰年就多加几天,这样最后就得到了出生到现在的天数。代码实现如下:

#include<stdio.h>
int Before(int F_sign,int day);
int After(int F_sign,int day);
int B_mounth(int birthday,int day);
int A_mounth(int now,int day);
#define SIZE 4
#define LONG 4
int main(void)
{
	int birthday[SIZE],now[LONG],Y_count,D_count,F_sign,num,S_sign,T_sign,a,day;
	int i,j,k;
	printf("请输入的你的出生日期(年 月 日):(请用空格隔开)");
	printf("(输入非正常月份退出)\n");
	while(scanf("%d%d%d",&birthday[0],&birthday[1],&birthday[2])==3)
	{
		if(birthday[1]>12||birthday[1]<1)  break;
		printf("请输入今天的日期(年 月 日):(用空格隔开)\n"); 
		if(scanf("%d%d%d",&now[0],&now[1],&now[2])==3)
		{
			
			Y_count=(now[0]-birthday[0]-1)*365;                     //这里记录你的年龄并转换成天数,没有考虑年份。 
			F_sign=birthday[0];                                     //标记年份 
			++F_sign;
			
			for(;;)                   //这个for循环是为了找到离出生日期(不含)往后最近的闰年。
			{
				if(F_sign%4==0&&F_sign%100!=0||F_sign%400==0)
					break;
				else 
					F_sign++;
			} 
			num=0;
			
			for(;F_sign<now[0]&&(F_sign%4==0&&F_sign%100!=0)||F_sign%400==0;F_sign+=4)     //这里是为了找到从最近的闰年到去年里面包括了几个闰年。 
				num++;
			Y_count+=num;                                   //把闰年考虑进去了。
			F_sign=birthday[1]+1;                            //标记月份
			num=0;
			
			if(birthday[0]%4==0&&birthday[0]%100!=0||birthday[0]%400==0)           //计算出生的那年所经过的天数 
			   day=29;
			   else 
			   day=28;
			S_sign=Before(F_sign,day);
			T_sign=B_mounth(birthday[1],day);
			T_sign-=birthday[2];
			
			Y_count+=(S_sign+T_sign);
			
			F_sign=now[1];
			if(now[0]%4==0&&now[0]%100!=0||now[0]%400==0)		              //计算今年所经过的天数 
			day=29;
			else 
			day=28;
			
			S_sign=After(F_sign,day);
			T_sign=A_mounth(now[1],day);
			a=T_sign;
			T_sign-=now[2];
			T_sign=a-T_sign;
			
			Y_count+=(S_sign+T_sign);
			
			printf("你的年龄换算成天数一共是:%d\n",Y_count);
	}
		printf("请输入的你的出生日期(年 月 日):(请用空格隔开)\n");
	}
	return 0;
} 

int Before(int F_sign,int day)
{
	int num=0;
	while(F_sign<=12)                            
	{
	switch(F_sign)
		{
		case 1: num+=31;break;
		case 2: num+=day;break;
		case 3: num+=31;break;
		case 4: num+=30;break;
		case 5: num+=31;break;
		case 6: num+=30;break;
		case 7: num+=31;break;
		case 8: num+=31;break;
		case 9: num+=30;break;
		case 10: num+=31;break;
		case 11: num+=30;break;
		default:num+=31;
		}
		++F_sign;
		}
		return num;
}

int After(int F_sign,int day)
{
	int num=0;int time=1;
	while(time<F_sign)                            
	{
	switch(time)
		{
		case 1: num+=31;break;
		case 2: num+=day;break;
		case 3: num+=31;break;
		case 4: num+=30;break;
		case 5: num+=31;break;
		case 6: num+=30;break;
		case 7: num+=31;break;
		case 8: num+=31;break;
		case 9: num+=30;break;
		case 10: num+=31;break;
		case 11: num+=30;break;
		default:num+=31;
		}
		++time;
		}
		return num;
}

int B_mounth(int birthday,int day)
{
	int num;
	switch(birthday)
		{
		case 1: num=31;break;
		case 2: num=day;break;
		case 3: num=31;break;
		case 4: num=30;break;
		case 5: num=31;break;
		case 6: num=30;break;
		case 7: num=31;break;
		case 8: num=31;break;
		case 9: num=30;break;
		case 10: num=31;break;
		case 11: num=30;break;
		default:num=31;
		}
		return num;
}
int A_mounth(int now,int day)
{
	int num;
	switch(now)
		{
		case 1: num=31;break;
		case 2: num=day;break;
		case 3: num=31;break;
		case 4: num=30;break;
		case 5: num=31;break;
		case 6: num=30;break;
		case 7: num=31;break;
		case 8: num=31;break;
		case 9: num=30;break;
		case 10: num=31;break;
		case 11: num=30;break;
		default:num=31;
		}
		return num;
}

第四题
第四题题意希望我们使用自定义函数进行输出,这是为了让我们学习如何使用自定义函数。题目希望我们调用一次函数打印一次结果,但是这里为了方便,使用了for循环。
自定义函数由三部分组成,函数的返回值类型,函数名,函数的形式参数,如果函数没有返回值,应该写void,调用函数的时候,传给函数的参数类型应该和函数的形参相对应,如果函数没有形参,那么调用函数时也不需要写形参。第四题代码如下:

#include<stdio.h>

void Jolly();
void deny();                            //由于调用函数写在主调函数的后面,所以要先声明。 
int main(void)
{
	Jolly();                                //调用名为Jolly的函数 
	deny();
	return 0;
} 

void Jolly()                             //定义Jolly函数。 
{
	for(int i=0;i<3;i++)
	printf("For he`s a jolly good fellow!\n");
}

void deny()                               //定义deny函数 
{
	printf("Which nobody can deny!\n");
}

当调用函数的函数原型写在主调函数的后面的时候,应该在主调函数的前面声明被调函数,以告诉处理器存在这样的一个函数以供调用。以下是输出:
在这里插入图片描述
第五题
第五条题是为了让我们更熟练调用函数的写法,这题和第四题差不多。代码如下:

#include<stdio.h>

void br();
void ic();                            //由于调用函数写在主调函数的后面,所以要先声明。 
int main(void)
{
	br();ic();
	printf("\n");                    //换行                               
	ic();
	printf("\n");   
	br();
	printf("\n");   
	return 0;
} 

void br()                             //定义br函数。 
{
	printf("Brazil.Russia");
}

void ic()                               //定义ic函数 
{
	printf("India,China");
}

输出如下:
在这里插入图片描述
第六题
第六题是为了让我们了解算术运算符,这里要注意的是计算平方即原数乘上原数,立方同理可得。代码如下:

#include<stdio.h>

int main(void)
{
	const int toes=10;
	printf("The toes=%d\ntoes^2=%d\n2*toes=%d\n",toes,toes*toes,2*toes); //算术运算符“*”。 
	return 0;
 } 

输出如下:
在这里插入图片描述
第七题
第七题同样是自定义函数的题目,这里不多解释,代码如下:

#include<stdio.h>

void Smile();
int main()
{
	Smile();Smile();Smile();
	printf("\n");
	Smile();Smile();
	printf("\n");
	Smile();
	printf("\n");
	return 0;
}
void Smile()
{
	printf("Smile!");
}

输出如下:
在这里插入图片描述
第八题(终于到这章的最后一题了)
这题仍然是一题简单的调用函数题,代码如下:

#include<stdio.h>

void two();
void One_three();
int main(void)
{
	printf("starting now:\n");
	One_three();
	two();
	printf("done!\n");
	return 0;
}

void One_three()
{
	printf("one\n");
}
void two()
{
	printf("two\nthree\n");
}

输出如下:
在这里插入图片描述
好了本章到这里就基本结束了(除了第三题,你能初步的写出基本的c程序了吗,代码是不是使你快乐呢。。。)

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值