## 题目 题目链接:[hhuoj1310][1] ``` 1310: 平均绩点 时间限制: 1 Sec 内存限制: 32 MB 题目描述 每门课的成绩分为A、B、C、D、F五个等级,为了计算平均绩点,规定A、B、C、D、F分别代表4分、3分、2分、1分、0分。 输入 有多组测试样例。每组输入数据占一行,由一个或多个大写字母组成,字母之间由空格分隔。 输出 每组输出结果占一行。如果输入的大写字母都在集合{A,B,C,D,F}中,则输出对应的平均绩点,结果保留两位小数。否则,输出"Unknown"。 样例输入 A B C D F B F F C C A D C E F 样例输出 2.00 1.83 Unknown ``` ## 题解 ### C++/getline() 这个题目和之前的读入的问题又有了一点小小的改变。 在这个题目里面,每一行的输入的大写字母数量是未知的。所以这里我们就要单独读入一行,然后每一行再单独处理。 这里我使用的是 `getline()` 函数读入 `string`,使用这个函数需要引用头文件 ``。 这里 getline 有两种形式: ```cpp (1) istream& getline (istream& is, string& str, char delim); (2) istream& getline (istream& is, string& str); ``` 其中: - `is` 进行读入操作的输入流 - `str` 用来存储读入的内容 - `delim` 终止符,遇到该字符停止读取操作,不写的话默认为 `'\n'`,如定义2中的示例。 举例: ```cpp string str; while(getline(cin,str)); ``` 这里我们用 `if` 解决判断的问题(愿意写的话也可以用 `switch`)。 上代码: ```cpp #include #include #include using namespace std; int main() { int cnt=0; double tot=0; string in; while(getline(cin,in)) { bool flag=true; for(int i = 0;i < in.size();i++){ if(in[i]==' ') continue; else if(in[i]=='A') tot+=4; else if(in[i]=='B') tot+=3; else if(in[i]=='C') tot+=2; else if(in[i]=='D') tot+=1; else if(in[i]=='F'); else flag=false; cnt++; } if(flag) cout << fixed << setprecision(2) << tot/cnt << endl; else cout << "Unknown\n"; cnt=0; tot=0; } return 0; } ``` 参考网站: - [cpp reference 上对 getline 的解释][2] - [csdn 上的讲解][3] ### C++/stringstream 除了这样写以外,我们也可以使用 `stringstream` 来写。 这里得注意的就是 `stringstream` 的速度是非常非常慢的。因此这样的方法一般用在数据量不是太大、这样写又会方便很多的题目上。 使用 `stringstream`,我们首先要引入头文件 ``。 这里不解释如何使用 `stringstream`,请看代码理解: ```cpp #include #include #include #include using namespace std; int main() { int cnt=0; double tot=0; string in; while(getline(cin,in)) { bool flag=true; stringstream ss(in); char ch; while(ss >> ch) { if(ch=='A') tot+=4; else if(ch=='B') tot+=3; else if(ch=='C') tot+=2; else if(ch=='D') tot+=1; else if(ch=='F'); else flag=false; cnt++; } if(flag) cout << fixed << setprecision(2) << tot/cnt << endl; else cout << "Unknown\n"; cnt=0; tot=0; } return 0; } ``` 参考资源:算法竞赛入门经典(第2版)5.1.3 字符串 ### C语言/fgets() 对于 C 语言的选手(代码写多了早晚会变成 C++ 选手的 /xiao),可以选择用 `fgets` 读入每一行的数据,其他内容还是和 C++ 的写法一样。 这里要注意的就是 `fgets()` 会把结尾的换行符也读入,所以最后的 `strlen` 需要 -1。 ```c #include #include int main() { int cnt=0; double tot=0; char in[1024]; while(fgets(in,1024,stdin)) { bool flag=true; int len=strlen(in); for(int i = 0;i < len-1;i++){ if(in[i]==' ') continue; else if(in[i]=='A') tot+=4; else if(in[i]=='B') tot+=3; else if(in[i]=='C') tot+=2; else if(in[i]=='D') tot+=1; else if(in[i]=='F'); else flag=false; cnt++; } if(flag) printf("%.2f\n",tot/cnt); else puts("Unknown"); cnt=0; tot=0; } return 0; } ``` 提供参考的网站: - [cpp reference 对 fgets() 的解释][4] - [博客园上的 gets 和 fgets 的区别讲解][5] ps:`gets` 因为可能导致内存越界,所以在 C++11 的标准里面已经弃用(但是据说在编译器上还是能用)。 [1]: http://acm.hhu.edu.cn/problem.php?id=1310 [2]: http://www.cplusplus.com/reference/string/string/getline/ [3]: https://www.cnblogs.com/ymd12103410/p/9514896.html [4]: http://www.cplusplus.com/reference/cstdio/fgets/ [5]: https://www.cnblogs.com/aexin/p/3908003.html Loading... ## 题目 题目链接:[hhuoj1310][1] ``` 1310: 平均绩点 时间限制: 1 Sec 内存限制: 32 MB 题目描述 每门课的成绩分为A、B、C、D、F五个等级,为了计算平均绩点,规定A、B、C、D、F分别代表4分、3分、2分、1分、0分。 输入 有多组测试样例。每组输入数据占一行,由一个或多个大写字母组成,字母之间由空格分隔。 输出 每组输出结果占一行。如果输入的大写字母都在集合{A,B,C,D,F}中,则输出对应的平均绩点,结果保留两位小数。否则,输出"Unknown"。 样例输入 A B C D F B F F C C A D C E F 样例输出 2.00 1.83 Unknown ``` ## 题解 ### C++/getline() 这个题目和之前的读入的问题又有了一点小小的改变。 在这个题目里面,每一行的输入的大写字母数量是未知的。所以这里我们就要单独读入一行,然后每一行再单独处理。 这里我使用的是 `getline()` 函数读入 `string`,使用这个函数需要引用头文件 `<string>`。 这里 getline 有两种形式: ```cpp (1) istream& getline (istream& is, string& str, char delim); (2) istream& getline (istream& is, string& str); ``` 其中: - `is` 进行读入操作的输入流 - `str` 用来存储读入的内容 - `delim` 终止符,遇到该字符停止读取操作,不写的话默认为 `'\n'`,如定义2中的示例。 举例: ```cpp string str; while(getline(cin,str)); ``` 这里我们用 `if` 解决判断的问题(愿意写的话也可以用 `switch`)。 上代码: ```cpp #include <iostream> #include <string> #include <iomanip> using namespace std; int main() { int cnt=0; double tot=0; string in; while(getline(cin,in)) { bool flag=true; for(int i = 0;i < in.size();i++){ if(in[i]==' ') continue; else if(in[i]=='A') tot+=4; else if(in[i]=='B') tot+=3; else if(in[i]=='C') tot+=2; else if(in[i]=='D') tot+=1; else if(in[i]=='F'); else flag=false; cnt++; } if(flag) cout << fixed << setprecision(2) << tot/cnt << endl; else cout << "Unknown\n"; cnt=0; tot=0; } return 0; } ``` 参考网站: - [cpp reference 上对 getline 的解释][2] - [csdn 上的讲解][3] ### C++/stringstream 除了这样写以外,我们也可以使用 `stringstream` 来写。 这里得注意的就是 `stringstream` 的速度是非常非常慢的。因此这样的方法一般用在数据量不是太大、这样写又会方便很多的题目上。 使用 `stringstream`,我们首先要引入头文件 `<sstream>`。 这里不解释如何使用 `stringstream`,请看代码理解: ```cpp #include <iostream> #include <string> #include <sstream> #include <iomanip> using namespace std; int main() { int cnt=0; double tot=0; string in; while(getline(cin,in)) { bool flag=true; stringstream ss(in); char ch; while(ss >> ch) { if(ch=='A') tot+=4; else if(ch=='B') tot+=3; else if(ch=='C') tot+=2; else if(ch=='D') tot+=1; else if(ch=='F'); else flag=false; cnt++; } if(flag) cout << fixed << setprecision(2) << tot/cnt << endl; else cout << "Unknown\n"; cnt=0; tot=0; } return 0; } ``` 参考资源:算法竞赛入门经典(第2版)5.1.3 字符串 ### C语言/fgets() 对于 C 语言的选手(代码写多了早晚会变成 C++ 选手的 /xiao),可以选择用 `fgets` 读入每一行的数据,其他内容还是和 C++ 的写法一样。 这里要注意的就是 `fgets()` 会把结尾的换行符也读入,所以最后的 `strlen` 需要 -1。 ```c #include <stdio.h> #include <string.h> int main() { int cnt=0; double tot=0; char in[1024]; while(fgets(in,1024,stdin)) { bool flag=true; int len=strlen(in); for(int i = 0;i < len-1;i++){ if(in[i]==' ') continue; else if(in[i]=='A') tot+=4; else if(in[i]=='B') tot+=3; else if(in[i]=='C') tot+=2; else if(in[i]=='D') tot+=1; else if(in[i]=='F'); else flag=false; cnt++; } if(flag) printf("%.2f\n",tot/cnt); else puts("Unknown"); cnt=0; tot=0; } return 0; } ``` 提供参考的网站: - [cpp reference 对 fgets() 的解释][4] - [博客园上的 gets 和 fgets 的区别讲解][5] ps:`gets` 因为可能导致内存越界,所以在 C++11 的标准里面已经弃用(但是据说在编译器上还是能用)。 [1]: http://acm.hhu.edu.cn/problem.php?id=1310 [2]: http://www.cplusplus.com/reference/string/string/getline/ [3]: https://www.cnblogs.com/ymd12103410/p/9514896.html [4]: http://www.cplusplus.com/reference/cstdio/fgets/ [5]: https://www.cnblogs.com/aexin/p/3908003.html Last modification:March 13, 2019 © Allow specification reprint Support Appreciate the author Like 如果觉得我的文章对你有用,请随意赞赏