C++:如果提供,则从文件读取(写入)文件,否则回退到 std::cin (std::cout)

C++ : Read(Write) from(to) a file if provided otherwise fall back to std::cin (std::cout)

我有这个需求。读取或写入 from/to 文件(如果提供)否则回退给好朋友 std::cin / std::cout,如:

// pseudo code for problem statement.

int main(int argc, char* argv[]) 
{
  istream reader;
  ostrea writer;
  if (argc > 1) 
  {
    // we have path to our file in argv[] 
    reader = ifstream(infile);
    writer = ofstream(outfile);
  }
  else
  {
    reader = cin;
    writer = cout;
  }
 // rest of code
}

本质上,即使我的思路很绕,有没有办法实现类似的目标。 谢谢!

使用的环境:C++ 11、14、17。

编辑#1: 详细说明if条件,如果程序调用为

$: driver "input_file.txt" "output_file.txt"

它应该从这些文件做IO,相反,如果这样调用,

$: driver < "input_file.txt" > "output_file.txt" 

它应该使用 std::cinstd::cout

// 编辑#1 结束

我正在通读参考文献 here,我在想这是否有帮助?

你可以看看下面的方法:

void read_write(ifstream&, ofstream&);  // Overloaded reader-writer
void read_write(istream&, ostream&);

int main(int argc, char* argv[]) {
    if (argc > 1) {
        auto infile = argv[1];
        auto outfile = argv[2]
        read_write(infile, outfile);
    } else read_write(cin, cout);
    // rest of code
}

您可以使用指向 std::ostreamstd::istream 的基类的指针:

#include <iostream>

int main(int argc, char* argv[]) 
{
  std::istream* reader;
  std::ostream* writer;
  bool deleteNeeded;
  if (argc > 1) 
  {
    // mark them for deletion, using a bool, for example
    deleteNeeded = true;
    // we have path to our file in argv[] 
    reader = new ifstream(infile);
    writer = new ofstream(outfile);
  }
  else
  {
    // mark for no deletion, setting the same bool
    deleteNeeded = false;

    reader = &std::cin;
    writer = &std::cout;
  }
  // rest of code
  if(deleteNeeded) 
  {
    delete reader; delete writer;
  }
}

或者使用可以重新分配的引用之类的东西。

我尝试了 post 建议并感谢大家,这就是我想出的。

#include <iostream>
#include <fstream>

void solve(std::istream& in, std::ostream& out) {
  int n;
  in >> n;
  out
    << n << " squared is " 
    << static_cast<uint64_t>(n)*n << " !" 
    << std::endl;
}

int main(int argc, char* argv[]) {
  if (argc > 1) {
    std::ifstream in(argv[1]);
    std::ofstream out(argv[2]);
    solve(in, out);
  } else {
    solve(std::cin, std::cout);
  } 
}

// call : ./driver in.txt out.txt