我编写了以下简单的C ++结构实现来查看结构指针的用法。
#include <iostream>
struct Employee
{
std::string name;
std::string sex;
int e_id;
}emp[2];
void printEmployee(struct Employee *e)
{
std::cout << e->name << std::endl;
std::cout << e->sex << std::endl;
std::cout << e->e_id << std::endl;
}
int main(int argc, char const *argv[])
{
struct Employee *e_ptr;
e_ptr = emp;
for (int i = 0; i < 2; ++i)
{
std::getline(std::cin, emp[i].name);
std::getline(std::cin, emp[i].sex);
std::cin >> emp[i].e_id;
}
for (int i = 0; i < 2; ++i)
{
printEmployee(e_ptr+i);
std::cout << std::endl;
}
return 0;
}
输入
John Smith
male
123
Sarah Collin
female
在这些输入之后,程序显示输出,尽管代码应该再输入一次。输出是
John Smith
male
123
Sarah Collin
0
但如果我不包含int e_id
作为成员,那么代码就可以完美运行。
答案 0 :(得分:2)
这是混合getline和cin。 Getline读入输入,直到它到达(通常)换行符'\ n'。它将所有内容都移到换行符,然后扔掉换行符。
cin读取,直到你击中空白区域(比如说换行符),但不会将其从流中抛出。因此,您输入123 ENTER,这意味着您在流中有123 \ n。 Cin占据了123,但离开了\ n。
现在你回到员工姓名的getline,然后立即看到流中的\ n,这意味着它已经完成了,它就把它扔掉了。出于好奇,如果您键入123 SPACE而不是输入?
,它是否有效所以实际发生的事情是约翰史密斯是好的,男性是好的,123是好的,但是第二个员工的名字被忽略了,你输入Sarah Collin进行技术上的性别,然后键入女性应该是什么E_ID。由于女性不是整数,会发生什么?默认情况下,Cin进入错误状态并跳过进一步的cin操作(您也可以将其配置为抛出异常)。所以实际上你实际上从来没有为第二个e_id输入任何东西,你看到的0就是它创建时的情况(你从未初始化它,所以它实际上可能是任何值!读取未初始化的值是未定义的行为。您的编译器可以通过将int设置为0来帮助您,但这不是您可以依赖的善意。
这是其他人提出您的问题,以及如何使用
的示例cin.ignore();
解决这个问题。您需要手动忽略该换行符。
答案 1 :(得分:2)
当读取整数std::cin
遇到[+][-][0-9]
以外的字符时停止。也就是说,std::cin
停止在一个字符中,该字符不能包含在整数的有效表示中。
在第三行输入中,有4个字符为123\n
。
在阅读std::string
时,std::getline
会在遇到\n
或删除字符时停止阅读字符。此外,std::getline
不会在读取的字符串中存储\n
或删除字符。
因此,std::cin
按预期读取整数emp[0].e_id
并停在\n
。在此std::getline
读取\n
后,停止并在emp[1].name