初学acmer--读《算法竞赛入门经典》笔记(三)p27-34
来源:互联网 发布:tomcat80端口被占用 编辑:程序博客网 时间:2024/04/29 19:27
题目:数据统计 (p27-32)
输入一些整数,求出它们的最小值、最大值和平均值(保留三位小数),输入保证这些数都是不超过1000的整数
样例输入
2 8 3 5 1 7 3 6
样例输出
1 8 4.375
先给代码(有bug)
#include<stdio.h>int main() {int x,n=0,min,max,s=0;while(scanf("%d",&x)==1){s+=x;if(x<min)min=x;if(x>max)max=x;n++;}printf("%d %d %.3f\n",min,max,(double)s/n);return 0;}
1.scanf()函数返回成功输入的变量个数,当输入结束时,scanf函数无法读取变量,将返回零
2.在Windows下,输入完毕后先按Enter键,再按Ctrl+Z键,最后按Enter键即可结束输入
在Linux下,输入完毕后按Ctrl+D键即可结束输入
3.但是输出结果却是不确定的,通过输出中间结果的方法,很容易发现变量max,min一开始未初始化
书上解决方法:可以用一个很小的值来初始化max;用一个很大的值来初始化min;
本题中可以使INF=1000;max=-INF;min=INF;
自己想法:min,max都用第一个读取的数来初始化
代码如下:
#include<stdio.h>int main() {int x,n=0,min,max,s=0;while(scanf("%d",&x)==1){s+=x;min=x;max=x;n++; //min,max都用第一个读取的数来初始化while(scanf("%d",&x)==1){s+=x;if(x<min)min=x;if(x>max)max=x;n++;}break;}printf("%d %d %.3f\n",min,max,(double)s/n);return 0;}
4.本题是手动输入,略显麻烦,可以采取文件输入方式使用文件最简单的方法是使用输入输出重定向,只需在main函数的入口处加入两条语句:
freopen("input.txt","r",stdin);
freopen("output.txt","w",stdout);
ps:在算法竞赛中,首先要弄清是标准输入输出,还是文件输入输出?如果是文件输入输出,是否禁止用重定向方式访问文件
另外也要严格遵守文件名规定,包括程序文件名和输入输出文件名。不要弄错大小写,不要拼错文件名,不要使用绝对路径或相对路径
5.当然,即使比赛要求是标准输入输出,也可以使用文件输入输出,可以避免繁琐的手动输入输出,但是最后提交时可以用条件编译指令将重定向语句删掉
代码如下:
#include<stdio.h>#define LOCAL //在标准输入输出比赛中,最后要记得注释掉这一行#define INF 1000 int main() {#ifdef LOCALfreopen("input.txt","r",stdin); freopen("output.txt","w",stdout); #endifint x,n=0,min=INF,max=-INF,s=0;while(scanf("%d",&x)==1){s+=x;if(x<min)min=x;if(x>max)max=x;n++;}printf("%d %d %.3f\n",min,max,(double)s/n);return 0;}6.如果比赛要求用文件输入输出,但禁止用重定向的方式,代码如下:
#include<stdio.h>#define INF 1000 int main() {FILE *fin,*fout;fin=fopen("data.in","rb");fout=fopen("data.out","wb");int x,n=0,min=INF,max=-INF,s=0;while(fscanf(fin,"%d",&x)==1){s+=x;if(x<min)min=x;if(x>max)max=x;n++;}fprintf(fout,"%d %d %.3f\n",min,max,(double)s/n);fclose(fin);fclose(fout);return 0;}ps:重定向和fopen两种方法各有优劣
重定向简单自然,但是不能同时读写文件和标准输入输出
fopen的写法较为繁琐,但是灵活性比较大,例如可以反复打开并读写文件,也可以通过赋值“fin=stdin;fout=stout”并删掉调用fopen和fclose语句来改成标准输入输出
题目:数据统计|| (p32-34)
输入一些整数,求出它们的最小值、最大值和平均值(保留三位小数),输入保证这些数都是不超过1000的整数
输入包含多组数据,每组数据第一行是整数个数n,第二行是n个整数。n=0为输入结束标志,程序应当忽略这组数据。相邻两组数据之间应输出一个空行
样例输入
8
2 8 3 5 1 7 3 6
4
-4 6 10 0
0
样例输出
Case 1:1 8 4.375
Case 2:-4 10 3.000
老规矩,先贴代码(有bug):
#include<stdio.h>#define INF 1000 int main() {int x,n=0,min=INF,max=-INF,s=0,kase=0;while(scanf("%d",&n)==1&&n){ int s=0; for(int i=0;i<n;i++) { scanf("%d",&x); s+=x;if(x<min)min=x; if(x>max) max=x; }if(kase) printf("\n"); //为了符合题目“相邻两组数据之间应输出一个空行”这一要求printf("Case %d: %d %d %.3f\n",++kase,min,max,(double)s/n);}return 0;}1.程序之所以仍然判断scanf的返回值,是为了提高代码的鲁棒性,即为了防止比赛数据有瑕疵
2.kase的使用是为了符合题目“相邻两组数据之间应输出一个空行”这一要求
3.当在样例输入的最后增加第三组数据:1 0
输出为Case 3:-4 10 0.000
很明显,这是上一组的数据结果
由此可见:在多数据的题目中,一个常见错误是:在计算完上一组数据后,某些重复使用的变量没有重置,从而影响到下一组数据的结果
- 初学acmer--读《算法竞赛入门经典》笔记(三)p27-34
- 初学acmer--读《算法算法竞赛入门经典》笔记(12) P73-74
- 初学acmer--读《算法竞赛入门经典》笔记(一)P12-23
- 初学acmer--读《算法竞赛入门经典》笔记(二) p25-27
- 初学acmer--读《算法竞赛入门经典》笔记<四>(p36-41)
- 初学acmer--读《算法竞赛入门经典》笔记(五)P41-45
- 初学acmer--读《算法竞赛经典入门》笔记(六)p45-48
- 初学acmer--读《算法竞赛经典入门》笔记(七)P48-50
- 初学acmer--读《算法竞赛入门经典》笔记(八)p50-52
- 初学acmer--读《算法竞赛入门经典》笔记(11)P61-65
- 初学acmer--读《算法竞赛入门经典》笔记 p110-111 Uva101
- 初学acmer--《算法竞赛经典入门》笔记(九) P52-53
- 初学acmer--《算法竞赛入门经典》笔记(十)P54-56
- 初学acmer--《算法竞赛经典入门》读书笔记(暴力专题)P182
- 初学acmer--《算法竞赛经典入门》第二章2.5 习题自己的解答
- 《算法竞赛入门经典》笔记
- 算法竞赛入门经典 第一,二,三章学习笔记
- 算法竞赛入门经典读书笔记(三)7.2枚举排列
- 简单工厂模式--女娲造人造啥做啥
- Android 带关闭按钮的DialogFragment。
- C++中函数表与函数容器
- 理解MySQL——索引与优化
- 七牛上传图片第一次成功后面不成功
- 初学acmer--读《算法竞赛入门经典》笔记(三)p27-34
- How to fix the problem of executing gitenv.csh file failed
- JavaWeb使用Struts2的简单案例
- 11.6 字符串示例:字符串排序
- 11.5 字符串:选择排序
- 14.1 结构和其他数据形式:结构体
- 14.2 结构和其他数据形式:嵌套结构
- 14.5 结构和其他数据形式:指针和结构
- 微信小程序(5)-新闻页面制作(1)