从文本文件读取,然后将项目存储到列表中
Reading from text file and then store the item into a list
Im 试图读取名为stock.txt
的文件,该文件包含以下值:
ID、项目、颜色、尺寸、数量、价格
11,T-shirt,blue,XL,2,10.500000
12,Supreme,red,M,10,20.500000
13,BANG,red,M,10,20.500000
我想将每个项目存储在列表中,我该怎么做?
int main() {
ifstream infile;
infile.open("Stock.txt");
string id; string title; string colour; string size; string quantity; string cost;
//If file open is successful
while(infile.good()){
getline(infile,id,',');
getline(infile,title,',');
getline(infile,colour,',');
getline(infile,size,',');
getline(infile,quantity,',');
getline(infile,cost,'n');
}
infile.close();
}
您应该使用更现代的C++方法。
如果您可以研究此解决方案并尝试将来使用某些功能,我将很高兴。
在面向对象的世界中,我们使用类(或结构(,并将数据和函数放在一个(封装的(对象中,对这些数据进行操作。
只有类应该知道如何读取和写入其数据。不是一些外部全局函数。因此,我在您的结构中添加了 2 个成员函数。我已经覆盖了机械臂和提取器运算符。
在提取器中,我们将使用现代C++算法,将字符串拆分为标记。为此,我们有std::sregex_token_iterator
.而且因为有一个专门的功能用于此目的,我们应该使用它。此外,它非常简单。
使用下面的单行代码,我们将整个字符串拆分为标记,并将生成的标记放在std::vector
std::vector token(std::sregex_token_iterator(line.begin(), line.end(), delimiter, -1), {});
然后,我们将结果数据复制到成员变量中。
对于演示输出,我还覆盖了机械臂操作员。现在,您可以将外部操作器和机械臂运算符(">>"和"<<"(用于 Stock 类型的变量,就像任何其他C++整变量一样。
总的来说,我们也使用一种超简单的方法。首先,我们打开文件并检查这是否正常。
然后我们定义一个变量"stocks"(Astd::vector
of Stocks(,并使用其范围构造函数和std::istream_operator
来读取完整的文件。而且,由于该应用程序具有覆盖的提取器运算符,因此它知道如何读取并将为我们解析完整的CSV文件。
再次,非常简单和简短的单行
std::vector stocks(std::istream_iterator<Stock>(inFile), {});
将读取完整的源文件、所有行,解析行并将成员变量存储在生成的std::vector
的单个库存元素中。
#include <string>
#include <iostream>
#include <vector>
#include <fstream>
#include <regex>
#include <iterator>
#include <algorithm>
std::regex delimiter{ "," };
struct Stock {
// The data. Member variables
std::string id{};
std::string title{};
std::string colour{};
std::string size{};
std::string quantity{};
std::string cost{};
// Overwrite extractor operator
friend std::istream& operator >> (std::istream& is, Stock& s) {
// Read a complete line
if (std::string line{}; std::getline(is, line)) {
// Tokenize it
std::vector token(std::sregex_token_iterator(line.begin(), line.end(), delimiter, -1), {});
// If we read at least 6 tokens then assign the values to our struct
if (6U <= token.size()) {
// Now copy the data from the vector to our members
s.id = token[0];
s.title = token[1];
s.colour = token[2];
s.size = token[3];
s.quantity = token[4];
s.cost = token[5];
}
}
return is;
}
// Overwrite inserter operator
friend std::ostream& operator << (std::ostream& os, const Stock& s) {
return os << "ID: " << s.id << "nTitle: " << s.colour
<< "nSize: " << s.size << "nQuantity: " << s.quantity << "nCost: " << s.cost;
}
};
int main() {
// Open file and check, if it could be opened
if (std::ifstream inFile("stock.txt"); inFile) {
// Define the variable and use range constructor to read and parse the complete file
std::vector stocks(std::istream_iterator<Stock>(inFile), {});
// Show result to the user
std::copy(stocks.begin(), stocks.end(), std::ostream_iterator<Stock>(std::cout, "n"));
}
return 0;
}
请注意:我使用的是 C++17,可以在没有模板参数的情况下定义 std::vector。编译器可以从给定的函数参数推断参数。此功能称为 CTAD("类模板参数推导"(。
此外,您可以看到我没有明确使用"end(("迭代器。
此迭代器将从具有正确类型的空大括号括起来的初始值设定项列表构造,因为由于 std::vector 构造函数需要它,它将被推导出为与第一个参数的类型相同。
您应该使用class
或struct
对每一行进行建模:
struct Record
{
int id;
std::string title;
std::string colour;
std::string size;
int quantity;
double price;
friend std::istream& operator>>(std::istream& input, Record & r);
};
std::istream& operator>>(std::istream& input, Record & r)
{
char comma;
input >> r.id;
input >> comma;
std::getline(input, r.title, ',');
std::getline(input, r.colour, ',');
std::getline(input, r.size, ',');
input >> r.quantity;
input >> comma;
input >> r.price;
input.ignore(100000, 'n');
return input;
}
现在您可以读入列表:
std::list<Record> database;
Record r;
while (infile >> r)
{
database.push_back(r);
}
operator>>
的重载使代码更简单、更易于阅读。
- 将文件内容存储到unordered_map仅存储最后的项目和值
- 从文本文件读取,然后将项目存储到列表中
- 自动完成在git存储库中的Visual Studio项目中不起作用
- git 子模块的替代方案,用于使用多个存储库的项目
- OpenCV:文件存储操作员">>"在一个项目中工作,但不在另一个项目中工作(在同一类上)
- bazel 项目将其".so"文件存储在哪里?
- 鸟类调查中的项目在代码中遇到问题.如何像数据库系统一样存储数据
- 带有数据存储库的C Bazel项目
- 是放置在存储在堆栈或堆中的unordered_map中的项目
- 在开源项目中存储 OAuth 机密
- 如何将 .c 和 .h 文件存储在包含路径中,与当前项目的源代码分开
- 将十六进制值存储为字符串(Arduino项目)
- 将项目存储在地图中的多个键下
- 是否可以将 VS C++ 项目生成的 DLL/EXE 项目存储在 NuGet 包中
- 如何在多个 GIT 存储库中组织大型项目
- 如何在C++中存储从 Vector 弹出的项目
- 其中是调试信息(断点等)存储在本机C++dll项目VS2013中的位置
- QList如何决定是存储指针还是存储项目本身
- Visual Studio: c++项目包含路径在存储库上共享
- 我应该在什么时候为我的项目创建一个存储库