C++如何使用getline()从txt文件读取字符串并存入string变量
我有一个存储了若干信息的.txt文件:
原有读取逻辑代码:
ifstream readfile(fileName); if (readfile) { readfile >> n; array = new Zakaz[n]; for (int i = 0; i < n; i++) { readfile >> array[i].client.name; readfile >> array[i].client.tableNumber; getline(readfile, array[i].dish.nameOfDish); readfile >> array[i].client.fullDishQuantity; readfile >> array[i].dish.price; readfile >> array[i].time.hour; readfile >> array[i].time.minute; } }
运行时getline()无法读取到完整的菜品名称字符串,修复方式如下:
故障原因
C++流的>>读取运算符默认以空白字符(空格、换行符、制表符)作为内容分隔边界,读取完目标值后,不会消费流中残留的分隔符。
在上述代码里,每次用>>读完桌号、数量、价格、时间这类数值/不带空格的短字段后,行尾的换行符会一直留在输入缓冲区里。紧接着调用getline()时,函数会从当前缓冲区位置开始读取,碰到的第一个字符就是残留的换行符,会直接判定读取结束,返回空/截断的错误结果,自然拿不到完整的菜品名。
修复方案
在每次从>>读取切换到getline()读取之前,调用流的ignore()方法,把缓冲区里从上一次读取结束位置到当前行末尾的所有残留字符(包括结尾的换行符)全部清空,再调用getline()就能正常读取整行完整字符串,哪怕菜品名中包含空格也不会被截断。
修正后的代码:
#include <limits> // 必须引入该头文件才能使用numeric_limits ifstream readfile(fileName); if (readfile) { readfile >> n; // 读完第一行的总条数n之后,先清掉第一行末尾的残留换行 readfile.ignore(numeric_limits<streamsize>::max(), '\n'); array = new Zakaz[n]; for (int i = 0; i < n; i++) { readfile >> array[i].client.name; readfile >> array[i].client.tableNumber; // 清掉桌号字段后残留的换行,为getline读整行做准备 readfile.ignore(numeric_limits<streamsize>::max(), '\n'); getline(readfile, array[i].dish.nameOfDish); readfile >> array[i].client.fullDishQuantity; readfile >> array[i].dish.price; readfile >> array[i].time.hour; readfile >> array[i].time.minute; } }
注意事项
ignore的第一个参数传numeric_limits<streamsize>::max()代表忽略字符数没有上限,第二个参数'\n'代表忽略操作一直执行到碰到换行符为止,碰到换行符后会把这个换行符也一并忽略掉- 不要用仅清空空白符的
readfile >> ws替代上述写法,这种方式会跨行长时间吞掉所有空白,容易误删菜品名前的有效格式空格,也无法处理多出来的无效残留字符 - 第一次读取完总条数
n之后必须加一次清空操作,否则第一次循环读取第一条菜品记录时就会碰到读n残留的换行符,导致第一条数据读取异常
内容的提问来源于stack exchange,提问作者Umlace
相关产品推荐
相关产品推荐

