3

我对这条线感到困惑:

sum += a[s[i] - '0']; 

为了给出一些上下文,这是代码的其余部分:

#include <iostream>

using namespace std;

int main() {

    int a[5];
    for (int i = 1; i <= 4; i++)
        cin >> a[i];
    string s;
    cin >> s;
    int sum = 0;
    for (int i = 0; i < s.size(); i++)
        sum += a[s[i] - '0'];
    cout << sum << endl;
    return 0;
}
4

2 回答 2

6

- '0'(或不太便携- 48,仅适用于ASCII)用于通过十进制代码将数字字符手动转换为整数,C++(和 C)保证所有编码中的连续数字。

例如,在EBCDIC240中,代码范围从for'0'249for '9',这适用于- '0',但会因- 48) 而失败。仅出于这个原因,最好始终- '0'像您一样使用该符号。

对于 ASCII 示例,如果'1'的 ASCII 码是49并且'0'的 ASCII 码是48, 49 - 48 = 1, 或采用推荐的格式'1' - '0' = 1

因此,正如您现在可能已经知道的那样,您可以使用这个简单的算术将所有 10 位数字从字符转换,只需减去'0',在另一个方向上,您可以通过添加将所有数字转换为其字符编码'0'

除此之外,代码中还有一些其他问题:

  • 数组不会在 index 处开始填充0,而是在 index 处填充1,因此,例如,如果您的字符串输入是"10"+ suma[1]a[0]没有a[0]分配值,因此行为是 undefined,您需要注意这些情况。
for (int i = 0; i < 5; i ++)
    cin >> a[i];

更合适的是,索引 from04,因为数组有 5 个索引,如果你想输入从 1 到 5 的数字,你可以稍后1从索引中减去。

  • 正如评论部分所指出的,例如,带有字母字符的错误输入也会引发未定义的行为。
于 2020-04-02T14:49:27.750 回答
3

来自 C++ 标准(2.3 字符集)

  1. ... 在源和执行基本字符集中,上述十进制数字列表中 0 之后的每个字符的值都应比前一个字符的值大一。

因此,如果您有一个字符,例如“4”,那么要获得值 4,您可以编写“4”-“0”。

例如,如果你会这样写

sum += a[s[i]];

其中 i 是字符 '0' 那么实际上你将拥有

sum += a[s[48]];

如果使用 ASCII 编码或

sum += a[s[240]];

如果使用 EBCDIC 编码。

例如,从您可以编写的数字中获取字符的反向操作

int digit = 4;
char c = digit + '0';

注意 C++ 中数组的索引是从 0 开始的。

因此这个循环

for (int i = 1; i <= 4; i ++)
    cin >> a[i];

应该写成

for (int i = 0; i < 5; i ++)
    cin >> a[i];

此外,为了避免这样的错误,您可以使用基于范围的 for 循环,例如

for ( auto &item : a ) std::cin >> item;
于 2020-04-02T15:07:37.267 回答