10. 平均绩点

61 阅读5分钟

题目描述

每门课的成绩分为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

本节课你将学到的内容:

字符串的声明和初始化
字符串操作
字符串的输入输出
字符串的遍历
浮点数运算
getline函数
printf函数
flag编程思想

1.string的使用

字符表示单个字符,用单引号扩起来,比如'a';

字符串表示一个可变长度的字符序列,可以包括多个字符,用双引号扩起来,比如"hello";

2.引入头文件

使用 string类型必须包含头文件<string>,作为标准库, string也被定义在命名空间 std中。

#include <string>
using string;

3.字符串的声明和初始化

//默认初始化,s1是一个空的字符串
string s1;

//初始化一个hello的字符串
string s2 = "hello";

//连续5个字符a组成的字符串,即'aaaaa'
string s3(5,'a');

4.字符串操作

4.1使用+对字符串进行拼接操作,返回字符串连接之后的结果

string s1 = "hello";
string s2 = "world";
string s3 = s1 + " " + s2;

4.2使用size()获取字符串的长度

int length = s1.size();

4.3使用下标操作符[]访问字符串中的每一位字符

//从下标0开始,表示字符串的第一个字符
char c1 = s1[1];

4.4使用empty()来判断字符串是否为空

字符串为空返回true,否则返回false;

//字符串为空返回true,否则返回false;
if(s1.empty()){

}

5.字符串的输入输出

5.1可以使用标准库中的iostream来读写string,比如cin读取和cout输出

string s;
cin >> s;
cout << s << endl;

5.2cin只能读取空格之前的数据

假设word输入的数据为"hello world"

string word;
    //只读取到hello
    while(cin >> word){
        
        cout << word << endl;
}

5.3getline()可以读取所有的数据(包括空格)

假设word输入的数据为"hello world"

string word;
    //可以完整读取hello world
      getline(cin , word);
      cout << word << endl;
}

getline(cin, n)与 cin >> n 的区别

getline(cin, n)cin >> n
读取整行(含空格)遇到空格或换行符停止
自动处理换行符换行符可能残留在输入流中

代码编写

1.使用getline()接收数据

//定义变量接收输入的每一行字符串
string s;
//读取每一行字符串
while(getline(cin,s)){
    
}

2.定义sum表示分数总和和count表示数据个数

//分数总和
int sum = 0;

//分数的个数
int count = 0;

3.对字符串进行遍历

//遍历字符串
for(int i = 0;i < s.size(); i++){

}

4.字母转化成分数。A转换成4分,B转换成3分,C转换成2分,D转换成1分,F转换成0分,不在集合{A,B,C,D,F}中。则返回Unknown

//遍历字符串
for(int i = 0;i < s.size(); i++){
    if(s[i] == 'A'){
        sum += 4;
        count++;
    }else if(s[i] == 'B'){
        sum += 3;
        count++;
    }else if(s[i] == 'C'){
        sum += 2;
        count++;
    }else if(s[i] == 'D'){
        sum += 1;
        count++;
    }else if(s[i] == 'F'){
        sum += 0;
        count++;
    }else if(s[i] == ' '){
      continue;
    }else{
      cout << "Unknown" << endl;
      break;
    } 
}

5.按照题目的格式输出平均绩点,结果保留两位小数,sum/count的结果是浮点数,格式为两位小数

  1. 需要引入头文件<stdio.h><cstdio>
  2. 保留两位小数,可以用printf函数,格式字符串%.2f
printf("%.2f",sum / count);

6. 第一个问题,遇到{A,B,C,D,F}以及空格之外的字符时,会输出"Unknown",然后退出for循环,但是仍然执行printf语句,应该不执行printf语句

  1. if可以控制语句的执行
if(条件为真){
    printf("%.2f\n",sum / count);
},
  1. 首先给每一行字符串一个令牌,遇到{A,B,C,D,F}以及空格之外的字符,则把令牌换成令牌
//初始化一个真令牌
bool flag = true;

//在某种情况下,把真令牌换成假令牌
flag = flase;

//if判断flag为真就执行,为假就不执行
if(flag){

}
  1. 也可以使用0/1来替代bool
//初始化一个真令牌
int flag = 1;

//在某种情况下,把真令牌换成假令牌
flag = 0;

//if判断flag为真就执行,为假就不执行
if(flag){

}

6. 第二个问题,使用printf("%.2f\n",sum / count)的时候,输出的是一个两位有效数字的浮点数,但是定义变量sumcount都是整数,相除会截断小数部分,保留整数部分,例如3/2的结果是1而不是1.5

//将sum定义成double类型                                               
double sum = 0;

7.完整代码

#include <bits/stdc++.h>

using namespace std;

int main(){
    string s;
    while(getline(cin,s)){
        double sum = 0;
        int count = 0;
        bool flag = true;
        for(int i = 0;i < s.size(); i++){
            if(s[i] == 'A'){
                sum += 4;
                count++;
            }else if(s[i] == 'B'){
                sum += 3;
                count++;
            }else if(s[i] == 'C'){
                sum += 2;
                count++;
            }else if(s[i] == 'D'){
                sum += 1;
                count++;
            }else if(s[i] == 'F'){
                sum += 0;
                count++;
            }else if(s[i] == ' '){
                continue;
            }else{
               flag = false;
                cout << "Unknown" << endl;
               break;
            }
        }
        if(flag){
            printf("%.2f\n",sum/count);
        }

    }
    return 0;
}