使用 freopen 写入子目录

Write to subdirectory using freopen

我正在尝试使用 freopen 写入子目录中的文件:

freopen("output/output-1.txt", "w", stdout);

我试过将其更改为输出到当前目录并且它有效。当目标输出文件位于子目录中时,它会无错误地终止;但是没有创建文件。创建所需的目录并不能解决问题。

void write_to(int subtask, int tc){
    string output = string("testcases/subtask-") + to_string(subtask) + "-tc-" + to_string(tc);
    freopen(output.c_str(), "w", stdout);
}

int main(){
    for(int i = 1; i <= 25; i++){
        write_to(1, i);
        // rest of code to generate and cout test cases
    }
}

有人对此有解决方案吗?

阅读 freopen(3) 的文档。您应该测试并使用它的结果:

The freopen() function opens the file whose name is the string pointed to by path and associates the stream pointed to by stream with it. The original stream (if it exists) is closed.

关于它的 return 值:

Upon successful completion fopen(), fdopen() and freopen() return a FILE pointer. Otherwise, NULL is returned and errno is set to indicate the error.

所以你至少需要编码(如果在 Linux 或某些 POSIX 系统上)

void write_to(int subtask, int tc){
   string output = 
     string("testcases/subtask-") + to_string(subtask) 
      + "-tc-" + to_string(tc);
   FILE*outf = freopen(output.c_str(), "w", stdout);
   if (!outf) {
     perror(output.c_str());
     char pwdbuf[128];
     memset (pwdbuf, 0, sizeof(pwdbuf));
     getcwd(pwdbuf, sizeof(pwdbuf)-1);
     fprintf(stderr, "failure in %s\n", pwdbuf);
     exit(EXIT_FAILURE);
   }
}

(上面的代码不会解决您的问题,但会在错误时输出有意义的错误消息;也许您 运行 您的代码不在适当的当前目录中)

我还建议在 main 中用 fflush(stdout)fflush(NULL) 结束你的 for 循环。

如果在 Linux 或 POSIX 上,您可能改为在文件描述符级别工作(因此编写重定向代码),并使用 open(2) & dup(2)(使用 STDOUT_FILENO 作为dup2).

的第二个参数

如果 testcases 是您 $HOME 中的一个目录(即 ~/testcases/ 由您的 shell 扩展),您需要

string output =
  string (getenv("HOME")) + "/" 
  + string("testcases/subtask-") + to_string(subtask) 
  + "-tc-" + to_string(tc);