从文件中读取和写入 int 对
Read and write int pairs from file
我正在尝试从文件中读取和写入一系列 int 对。该文件看起来像这样:
0 6
12 24
48 33
23 24
80 79
我的目标是将每一对读入一个结构:
struct foo {
int a;
int b;
}
然后将每个结构压入堆栈。然而,事实证明,fstreams 很难处理此任务。现在,我的文件读取代码如下所示:
std::fstream fileStream(file, std::ios::in);
int a, b;
while (fileStream >> a >> b) {
myStack.push({ a, b });
}
我的输入可能如下所示(由于我的用途,我必须单独输入...):
inputFoo(foo bar) {
std::fstream fileStream(file, std::ios::out);
fileStream << bar.a << " " << bar.b;
}
但是,我觉得这不是我应该高效、安全地执行此操作的方式。我还有一个检查文件是否已经存在的函数,但我不确定它是否有效:
bool fileExists() {
std::ifstream stream;
return stream.good();
}
实际执行此操作的最佳方法是什么?
这样做
std::ifstream fileStream(file, std::ios::in);
while (!fileStream.eof()) {
foo f;
fileStream >> f.a>> f.b
myStack.push(f);
}
循环将结束读取整个文件
写出来会这样
std::ofstream fileStream(file, std::ios::in);
while (!myStack.isEmpty()) {
foo f;
f=myStack.pop();
fileStream << f.a<<" "<< f.b<<endl;
}
您不需要 fileExists()
功能。该函数中的流甚至没有打开。像这样检查:
std::fstream fileStream(file, std::ios::in);
if(!fileStream.is_open())
{
// handle the error
}
现在,如果您愿意,有几个不改变逻辑的建议:
- 使用
std::ifstream
作为输入,您可以省略 std::ios::in
参数
- 使用
std::ofstream
进行输出,您可以省略 std::ios::out
参数
重载 <<
和 >>
运算符 foo
:
struct foo
{
int a;
int b;
foo() : a(0), b(0) {} // default constructor to make it a little more c++ and less c
friend std::istream &operator>>(std::istream &is, foo &f);
std::ostream &operator<<(std::ostream &os)
{
return os << a << " " << b;
}
};
// Both can be friend, only operator<< can be member
std::istream &operator>>(std::istream &is, foo &f)
{
return is >> f.a >> f.b;
}
不仅可以向其传递文件流,还可以向其传递 std::cin
和 std::cout
(可能对调试和控制台输入输出有用)。您会这样阅读:
foo f;
while(fileStream >> f)
myStack.push(f);
写得更简单:
fileStream << bar;
关于您的评论,这是我唯一想到的:
const std::string filePath = "file.txt";
std::ifstream ifs(filePath);
if(ifs.is_open())
{
// read
}
else
{
std::ofstream ofs(filePath);
// write
}
我正在尝试从文件中读取和写入一系列 int 对。该文件看起来像这样:
0 6
12 24
48 33
23 24
80 79
我的目标是将每一对读入一个结构:
struct foo {
int a;
int b;
}
然后将每个结构压入堆栈。然而,事实证明,fstreams 很难处理此任务。现在,我的文件读取代码如下所示:
std::fstream fileStream(file, std::ios::in);
int a, b;
while (fileStream >> a >> b) {
myStack.push({ a, b });
}
我的输入可能如下所示(由于我的用途,我必须单独输入...):
inputFoo(foo bar) {
std::fstream fileStream(file, std::ios::out);
fileStream << bar.a << " " << bar.b;
}
但是,我觉得这不是我应该高效、安全地执行此操作的方式。我还有一个检查文件是否已经存在的函数,但我不确定它是否有效:
bool fileExists() {
std::ifstream stream;
return stream.good();
}
实际执行此操作的最佳方法是什么?
这样做
std::ifstream fileStream(file, std::ios::in);
while (!fileStream.eof()) {
foo f;
fileStream >> f.a>> f.b
myStack.push(f);
}
循环将结束读取整个文件
写出来会这样
std::ofstream fileStream(file, std::ios::in);
while (!myStack.isEmpty()) {
foo f;
f=myStack.pop();
fileStream << f.a<<" "<< f.b<<endl;
}
您不需要 fileExists()
功能。该函数中的流甚至没有打开。像这样检查:
std::fstream fileStream(file, std::ios::in);
if(!fileStream.is_open())
{
// handle the error
}
现在,如果您愿意,有几个不改变逻辑的建议:
- 使用
std::ifstream
作为输入,您可以省略std::ios::in
参数 - 使用
std::ofstream
进行输出,您可以省略std::ios::out
参数 重载
<<
和>>
运算符foo
:struct foo { int a; int b; foo() : a(0), b(0) {} // default constructor to make it a little more c++ and less c friend std::istream &operator>>(std::istream &is, foo &f); std::ostream &operator<<(std::ostream &os) { return os << a << " " << b; } }; // Both can be friend, only operator<< can be member std::istream &operator>>(std::istream &is, foo &f) { return is >> f.a >> f.b; }
不仅可以向其传递文件流,还可以向其传递
std::cin
和std::cout
(可能对调试和控制台输入输出有用)。您会这样阅读:foo f; while(fileStream >> f) myStack.push(f);
写得更简单:
fileStream << bar;
关于您的评论,这是我唯一想到的:
const std::string filePath = "file.txt";
std::ifstream ifs(filePath);
if(ifs.is_open())
{
// read
}
else
{
std::ofstream ofs(filePath);
// write
}