C博客作业02

第二次C博客作业


Q0.展示PTA总分

  • 单循环结构

  • 嵌套循环


Q1.本章学习总结

1.1 学习内容总结

  • 单循环结构(for语句)
    • 先判断再循环,常在知道循环次数时候使用
    • 表达式1为一个不参与循环的单次表达式,其可作为某一变量的初始化赋值语句,用来给循环控制变量赋初值,也可用来计算其它与for循环无关但先于循环部分处理的一个表达式
    • 表达式2为判断循环条件的语句,为真(1)时执行循环体语句,为假(0)时结束循环
    • 表达式3每次循环结束后执行一遍,然后再转到表达式2进行判断
    • 表达式1,2,3均可以为空,但必须要有一个“;”符号!并且它们都可以有多个表达式,中间用“,”连接
    • 循环体语句只有一句时可以省略大括号,但一般建议还是写上大括号方便阅读


	for (表达式1; 表达式2; 表达式3)   
	{
		循环体语句;    //需要被多次执行的内容
	}
	
  • 单循环结构(while和do-while语句)
    • 两者代码结构十分相似,但要注意do-while语句中while()后要加分号
    • while语句先判断再循环,do-while语句先循环再判断,两者一般都用于不知道循环次数的情况(知道次数也可用)
    • 表达式1、2为判断循环条件的语句,为真(1)时执行循环语句,为假(0)时结束循环
    • 由于do-while语句先循环再判断,导致它在第一次进入循环时就不符合条件的情况下,也会执行一次循环,而for、while语句会直接结束循环


	while (表达式1)   
	{
		循环语句1;
	}

	do
	{
		循环语句2;
	} while (表达式2);   
	
  • 简单案例:用三种单循环结构计算1+2+…+100的值

运行完毕后三者都计算出正确答案5050

  • 嵌套循环

    • 顾名思义,循环中再次进行循环,但要注意检查循环结构,经常会出现死循环的情况
    • 可以为多个for连用,while与for连用等等情况
    • 要特别注意什么时候要在外部循环后,内部循环前对某些变量进行初始化(如计算多个阶乘之和在每次执行完内部循环后都要重置项为1)
    • 注意循环次数,若有多个嵌套循环执行的次数会相当大,影响程序效率,需要想办法控制循环次数(如课本中的男人、女人、小孩搬砖问题)
  • continue与break语句

    • break语句:跳出本层循环(如果要跳出嵌套循环则还需要更多的break)
    • continue语句:跳出本次循环,进入下一轮循环,并且它只能用于循环语句中
        /*continue和break语句简单说明*/

	for (i = 1; i <= 5; i++)
	{
		if (i == 3)
			continue;    //当i的值为3时直接跳过了下面的printf(),执行下一次i=4时的循环
		printf("A");     //最终输出了4个A
	}

	for (i = 1; i <= 5; i++)
	{
		if (i == 3)
			break;       //当i的值为3时直接结束循环
		printf("A");     //最终仅输出了2个A
	}
	

1.2 本章学习体会

  • 进入到循环结构后,课程难度也慢慢上去了,题目的复杂程度一下子飙升了,需要我们更加努力的去思考
  • 这也意味着动手敲代码越来越重要!!只看书是很难解决疑问的!
  • 循环结构是可能是代码中最最最重要的一部分了,不会的问题一定要抓紧时间解决了,不然到了数组等部分会相当相当痛苦
  • 代码量的话这周把2840题库中除了链表以外的都做完了,所以下次开始就没有这个量了……


Q2.PTA实验作业

2.1 求幂级数展开的部分和

2.1.1 伪代码

    x为用户输入的数字
    result用于保存最终结果,初始值为0
    item用于记录每项的值,初始值为1
    i用于记录当前为第几项,初始为1
    flag1为分母,flag2为分子

    输入x

    while item大于0.00001
        result = result + item;
        flag1 = 1;
        flag2 = 1;
        for j = 1; j <= i; j++
            flag1 = flag1 * j;
        end for
        for j = 1; j <= i; j++
            flag2 = flag2 * x;
        end for
        item = flag2/flag1;
        i++;
    end while
    result = result + item;
    
    输出结果result

2.1.2 代码截图

2.1.3 造数据测试

输入数据 输出数据 备注
0 1.0000 x取最小值
1 2.7183
1.2 3.3201 题目的例子
5 148.4132 x取最大值
0.1 1.1052

2.1.4 PTA提交列表及说明

  • 第1、2个部分正确:取x=5时程序运行超时。删除了代码中所有运用pow()的部分,改为用for来计算次方。
  • 第3、4个部分正确:计算次方的循环中乘的值不正确,将j改成了x
  • 第5个部分正确:x=5时答案仍然错误,经多次F11测试和用计算器计算e的5次方后发现最后结果少算一项,在输出前补上了这一项

2.2 简单计算器

2.2.1 伪代码

	ch1保存上一次输入的符号
	ch2保存新输入的符号
	a为输入的数字
	result保存已经计算的结果
	flag用于记录是否出现非法运算,初始为0

	输入算式,读取第一个数字和符号
	result=第一个数字

	while ch1不为等号
		读取下一个数字和字符

		switch ch1的符号  
		为加号时:result = result + a; break;
		为减号时:result = result - a; break;
		为乘号时:result = result * a; break;
		为除号时:
			if 除数不为0
				result = result / a;
				break;
			else  
				flag = 1;
				break;
			end if
		为其他符号时:flag = 1; break;  
		end switch
		ch1 = ch2;  
	end while

	if flag值为0  
		输出result
	else  
		输出ERROR
	end if

2.2.2 代码截图

2.2.3 造数据测试

输入数据 输出数据 备注
1+2*10-10/2= 10 题目的例子
1= 1 最小表达式
2+2/0= ERROR 除数为0
2+2*3&4= ERROR 非法表达式
1+3-2*0= 0 结果为0的情况

2.2.4 PTA提交列表及说明

(采用了2840题库中第一次做这题时的提交列表)

  • 第1个部分正确:除数为0的情况忘记写上,补充上了上去
  • 第2、3个部分正确:补充完除数为0的情况后还优化了代码(反向优化),结果出现了最小表达式的错误,单独增加了第一个符号就是等号的判断
  • 答案正确(本次题库中的):再一次优化了代码,减少了变量和多余的判断

(2840题库中这题上次写的部分代码)


2.3 单词长度

2.3.1 伪代码

	flag记录是不是第一个输出的数字
	count记录长度
	ch记录字符
	flagLetter记录是否遇到过空格或点以外的字符

	do
	{
		输入句子,每次读取一个字符
		if 读入的不是空格或点
			count++;
			flagLetter = 1;
		end if
		if 遇到过空格和点以外的字符,且又遇到了空格或点
			if flag值为0
				输出第一个单词长度,不带任何空格
				flag = 1;
			else   
				输出单词长度,前面带一个空格
			end if
			count = 0;
			flagLetter = 0;  
		end if
	} while ch不是”.”

2.3.2 代码截图

2.3.3 造数据测试

输入数据 输出数据 备注
It's great to see you here. 4 5 2 3 3 4 题目的例子
. 空句子
apple. 5 一个单词
(空格)(空格)abc(空格)(空格)(空格)de f(空格)(空格). 3 2 1 开头结尾多空格,连续多个空格

2.3.4 PTA提交列表及说明

第1个部分正确:空句子、连续多个空格、开头结尾多空格测试点无法通过,一开始的代码是遇到空格、点就会输出一个长度,导致输出了很多不必要的0,之后将代码进行了优化,新增加了变量flagLetter来判断是否有遇见过字母或其他字符,有遇过再输出长度
第2-5个部分正确:空句子测试点过不了,这个纯属画蛇添足了,当时写这里的时候单独写了一段代码,空句子时输出长度为0(自己觉得非常完美!没有任何问题!),还找同学说吐槽你看这个PTA是不是有问题啊我这写的哪里有问题啊。后来有人过了这个测试点,问了一下才知道空句子什么都不能输出……于是删掉那段多余的代码就通过了


Q3.代码互评

3.1 二进制转十进制

同学代码

我的代码

  • 我的代码使用了数组,先保存下所有输入的数,再进行后面的步骤,同学的代码读取一个使用一个,效率更高
  • 我的代码将储存的数组反用,同学的代码正向读取正向使用
  • 我的代码使用了函数pow(),并且随着count的增加程序效率会越来越低,而同学的代码没有使用这个,效率很高
  • 我们的代码都使用了变量flag来记录是否有遇到非法数字并控制输出的内容

3.2 编程打印空心字符菱形

同学代码

我的代码

  • 同学的代码将菱形的上下部分的for循环分开来写,我的代码则是在一个大的for循环中完成
  • 我的代码单独使用了两个变量k和kk分别来记录字母前的空格数和菱形中间的空格数,同学的代码则是找出他们之间的关系式进行使用,相比下我的代码更利于阅读,同学的代码使用的变量更少,程序效率略高一些
  • 我们的代码中都有一个关键数字,即为(行数+1)/2
原文地址:https://www.cnblogs.com/silverash/p/11706878.html