Stroustrup Ex.7,第 4 章 - C++ 语法
Stroustrup Ex.7, Chap.4 - C++ Syntax
我是 C++ 的新手,和这里的许多其他人一样,我正在尝试从 Bjarne Stroustrup 的编程——使用 C++ 的原则和实践中学习它。
我坚持练习 7,第 4 章,其中的想法是编写一个计算器,当输入是 一个整数 and/or 一个字符串 后跟 字符(+、-、* 或 /),输出应宣布 "the sum/diff/prod/ratio of" 输入 1输入2就是结果;所以如果 ("two" 3 *) 是输入,输出应该是 "the product of 2 * 3 = 6".
这是 Stroustrup 的解决方案(我要留下 Stroustrup 的评论):
-- 没有侵权,因为都是他的网站--
/*The solution uses two functions (in addition to main():
initialize_numbers() to initialize the vector of number string
representations
get_number() to read a number that is either a string or a sequence of
digits
*/
vector<string> numbers; // representation of numbers as strings
// numbers[i] is the string representation for i
// for numbers[0] to numbers[numbers.size()-1]
void initialize_numbers()
{
numbers.push_back("zero");
numbers.push_back("one");
numbers.push_back("two");
numbers.push_back("three");
numbers.push_back("four");
numbers.push_back("five");
numbers.push_back("six");
numbers.push_back("seven");
numbers.push_back("eight");
numbers.push_back("nine");
numbers.push_back("ten"); // why not? :-)
}
int get_number()
{
const int not_a_symbol = numbers.size(); // not_a_symbol is a value that does not correspond
// to a string in the numbers vector
int val = not_a_symbol;
if (cin>>val) return val; // try to read an integer composed of digits
cin.clear(); // clear string after failed attempt to read an integer
string s;
cin>>s;
for (int i=0; i<numbers.size(); ++i) // see if the string is in numbers
if (numbers[i]==s) val = i;
if (val==not_a_symbol) error("unexpected number string: ",s);
return val;
}
int main()
try
{ initialize_numbers();
cout<< "please enter two floating-point values separated by an operator\n The operator can be + - * / % : ";
while (true) { // "forever"; that is until we give an unacceptable input or make a computations error
int val1 = get_number();
char op = 0;
cin>>op; // get the operator
int val2 = get_number();
string oper; // text appropriate for an operator
double result;
switch (op) {
case '+':
oper = "sum of ";
result = val1+val2;
break;
case '-':
oper = "difference between ";
result = val1-val2;
break;
case '*':
oper = "product of ";
result = val1*val2;
break;
case '/':
oper = "ratio of ";
if (val2==0) error("trying to divide by zero");
result = val1/val2;
break;
case '%':
oper = "remainder of ";
if (val2==0) error("trying to divide by zero (%)");
result = val1%val2;
break;
default:
error("bad operator");
}
cout << oper << val1 << " and " << val2 << " is " << result << '\n';
cout << "Try again: ";
}
}
更具体地说,我的问题出在以下部分:
int get_number()
{
const int not_a_symbol = numbers.size(); // not_a_symbol is a value that does not correspond
// to a string in the numbers vector
int val = not_a_symbol;
if (cin>>val) return val; // try to read an integer composed of digits
cin.clear(); // clear string after failed attempt to read an integer
等等等等......
}
在大背景下,我只是不明白这里发生了什么。我无法理解整个 get_number() 函数,以及它与其余代码的关系。
1 - 为什么将 number.size() 的值赋给 not_a_symbol?这有什么作用?
2 - if (cin >> val) - 为什么这是有条件的? val 是 == 向量数的大小,即 11,那么条件数是 11 吗?这有什么帮助?
它返回了什么?本身?
3 - // 尝试读取由数字组成的整数 - 这是如何完成的,为什么有帮助?
谢谢,抱歉问题的格式太长了。
在整个函数for
中get_number()
i
从0到小于numbers.size()
并放入i
其中不包含数字的输入字符串与 numbers
向量中的一个字符串相比变为 val
(因此您将数字名称转换为数字值)。之后,您检查 val
是否与向量 numbers
的大小相同,因为如果是,则没有匹配项(有人输入的单词不是您可以处理的任何数字的名称)。
From if (cin >> x) - Why can you use that condition? cin>>val
(cin 从输入读取到变量 val)将 return 如果输入至少一个字母则为 false。
如果您输入的数字没有字母,您可以 return 它(我们想要代表数字名称的字符串或普通数字)。
很抱歉带走你的答案,伙计,但我自己弄明白了,事情要简单得多(也聪明)。
for 循环正常工作,将输入字符串与向量中的字符串进行比较并返回相应的索引号。
但是将numbers.size()的值赋值给not_a_symbol的原因在于,如果第一个IF失败,只有到那时,第二个才会变为真,因为 val 已经初始化。这就是为什么有 2 个单独的 IF 语句而不是 IF-ELSE 的原因:ELSE 不会使先前初始化的 val 计数,因为来自字符串 "s" 的输入将接管,从而阻止 val 的初始值继续工作(val= not_a_symbol) 在 ELSE 中。
忘了函数,把它们都放在main里面:
int main() {
vector<string> numbers{ "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten" };
int not = numbers.size();
int val = numbers.size(); //val is initialized
string s;
cin >> s;
for (int i = 0; i<numbers.size(); ++i)
if (numbers[i] == s) val = i; // first IF; if this condition is not met, it will return val as it was initialized (val=numbers.size() or 11)
if (val == not) val = 88; // then this condition will be checked. It will be true. It will return val = 88 (a random number);
cout << "val is: " << val << "\n" << "not is: " << not << "\n";
}
所以,这不是将 val 与向量的元素数进行比较的问题,而是 val 已经等于它并且该事实在第一个条件失败时起作用的问题。
我是 C++ 的新手,和这里的许多其他人一样,我正在尝试从 Bjarne Stroustrup 的编程——使用 C++ 的原则和实践中学习它。
我坚持练习 7,第 4 章,其中的想法是编写一个计算器,当输入是 一个整数 and/or 一个字符串 后跟 字符(+、-、* 或 /),输出应宣布 "the sum/diff/prod/ratio of" 输入 1输入2就是结果;所以如果 ("two" 3 *) 是输入,输出应该是 "the product of 2 * 3 = 6".
这是 Stroustrup 的解决方案(我要留下 Stroustrup 的评论):
-- 没有侵权,因为都是他的网站--
/*The solution uses two functions (in addition to main():
initialize_numbers() to initialize the vector of number string
representations
get_number() to read a number that is either a string or a sequence of
digits
*/
vector<string> numbers; // representation of numbers as strings
// numbers[i] is the string representation for i
// for numbers[0] to numbers[numbers.size()-1]
void initialize_numbers()
{
numbers.push_back("zero");
numbers.push_back("one");
numbers.push_back("two");
numbers.push_back("three");
numbers.push_back("four");
numbers.push_back("five");
numbers.push_back("six");
numbers.push_back("seven");
numbers.push_back("eight");
numbers.push_back("nine");
numbers.push_back("ten"); // why not? :-)
}
int get_number()
{
const int not_a_symbol = numbers.size(); // not_a_symbol is a value that does not correspond
// to a string in the numbers vector
int val = not_a_symbol;
if (cin>>val) return val; // try to read an integer composed of digits
cin.clear(); // clear string after failed attempt to read an integer
string s;
cin>>s;
for (int i=0; i<numbers.size(); ++i) // see if the string is in numbers
if (numbers[i]==s) val = i;
if (val==not_a_symbol) error("unexpected number string: ",s);
return val;
}
int main()
try
{ initialize_numbers();
cout<< "please enter two floating-point values separated by an operator\n The operator can be + - * / % : ";
while (true) { // "forever"; that is until we give an unacceptable input or make a computations error
int val1 = get_number();
char op = 0;
cin>>op; // get the operator
int val2 = get_number();
string oper; // text appropriate for an operator
double result;
switch (op) {
case '+':
oper = "sum of ";
result = val1+val2;
break;
case '-':
oper = "difference between ";
result = val1-val2;
break;
case '*':
oper = "product of ";
result = val1*val2;
break;
case '/':
oper = "ratio of ";
if (val2==0) error("trying to divide by zero");
result = val1/val2;
break;
case '%':
oper = "remainder of ";
if (val2==0) error("trying to divide by zero (%)");
result = val1%val2;
break;
default:
error("bad operator");
}
cout << oper << val1 << " and " << val2 << " is " << result << '\n';
cout << "Try again: ";
}
}
更具体地说,我的问题出在以下部分:
int get_number()
{
const int not_a_symbol = numbers.size(); // not_a_symbol is a value that does not correspond
// to a string in the numbers vector
int val = not_a_symbol;
if (cin>>val) return val; // try to read an integer composed of digits
cin.clear(); // clear string after failed attempt to read an integer
等等等等...... }
在大背景下,我只是不明白这里发生了什么。我无法理解整个 get_number() 函数,以及它与其余代码的关系。
1 - 为什么将 number.size() 的值赋给 not_a_symbol?这有什么作用?
2 - if (cin >> val) - 为什么这是有条件的? val 是 == 向量数的大小,即 11,那么条件数是 11 吗?这有什么帮助? 它返回了什么?本身?
3 - // 尝试读取由数字组成的整数 - 这是如何完成的,为什么有帮助?
谢谢,抱歉问题的格式太长了。
在整个函数
for
中get_number()
i
从0到小于numbers.size()
并放入i
其中不包含数字的输入字符串与numbers
向量中的一个字符串相比变为val
(因此您将数字名称转换为数字值)。之后,您检查val
是否与向量numbers
的大小相同,因为如果是,则没有匹配项(有人输入的单词不是您可以处理的任何数字的名称)。From if (cin >> x) - Why can you use that condition?
cin>>val
(cin 从输入读取到变量 val)将 return 如果输入至少一个字母则为 false。如果您输入的数字没有字母,您可以 return 它(我们想要代表数字名称的字符串或普通数字)。
很抱歉带走你的答案,伙计,但我自己弄明白了,事情要简单得多(也聪明)。
for 循环正常工作,将输入字符串与向量中的字符串进行比较并返回相应的索引号。
但是将numbers.size()的值赋值给not_a_symbol的原因在于,如果第一个IF失败,只有到那时,第二个才会变为真,因为 val 已经初始化。这就是为什么有 2 个单独的 IF 语句而不是 IF-ELSE 的原因:ELSE 不会使先前初始化的 val 计数,因为来自字符串 "s" 的输入将接管,从而阻止 val 的初始值继续工作(val= not_a_symbol) 在 ELSE 中。
忘了函数,把它们都放在main里面:
int main() {
vector<string> numbers{ "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten" };
int not = numbers.size();
int val = numbers.size(); //val is initialized
string s;
cin >> s;
for (int i = 0; i<numbers.size(); ++i)
if (numbers[i] == s) val = i; // first IF; if this condition is not met, it will return val as it was initialized (val=numbers.size() or 11)
if (val == not) val = 88; // then this condition will be checked. It will be true. It will return val = 88 (a random number);
cout << "val is: " << val << "\n" << "not is: " << not << "\n";
}
所以,这不是将 val 与向量的元素数进行比较的问题,而是 val 已经等于它并且该事实在第一个条件失败时起作用的问题。