将Windows cmd标准输出和stderr重定向到单个文件

rip*_*234 656 windows command-line cmd pipe

我正在尝试将DOS命令的所有输出(stdout + stderr)重定向到单个文件:

C:\>dir 1> a.txt 2> a.txt
The process cannot access the file because it is being used by another process.
Run Code Online (Sandbox Code Playgroud)

是可能的,还是应该重定向到两个单独的文件?

And*_*ahl 1032

你要:

dir > a.txt 2>&1
Run Code Online (Sandbox Code Playgroud)

语法2>&1将重定向2(stderr)到1(stdout).您还可以通过重定向到隐藏的信息NUL,在MSDN上更多的解释和例子.

  • 谢谢你,不知道这个unix shell语法也适用于DOS! (26认同)
  • 这非常适合隐藏所有输出..`net stop w3svc> NUL 2>&1` ..谢谢! (18认同)
  • 如果存在句柄,则句柄(即2)和重定向运算符(即>)之间不能有空格.因此`2> 2.txt`起作用(或`2>&1`)`2> 2.txt`不起作用; `2>&1`没有. (9认同)
  • 我非常喜欢这样."呃,这个小小的一次性问题需要一个小时".输入此评论比找到这个答案花了我更长的时间. (8认同)
  • @wasatchwizard Ithink我遇到了麻烦,但是> NUL 2> NUL工作正常 (2认同)
  • 真遗憾,微软没有本地T恤 (2认同)

Del*_*Jay 191

Anders Lindahl的回答是正确的,但是应该注意的是,如果你将stdout重定向到文件并且想要重定向stderr那么你必须确保在重定向之后2>&1指定,否则它将无法工作.1>

REM *** WARNING: THIS WILL NOT REDIRECT STDERR TO STDOUT ****
dir 2>&1 > a.txt
Run Code Online (Sandbox Code Playgroud)

正确的方式:2>&1.要追加,请使用1>.

  • @igbgotiz 2>&1表示'将流2重定向到流1'.所以你需要先设置流1 (11认同)
  • 我花了几个小时才弄清楚DelboyJay出了什么问题!谢谢! (8认同)
  • 它是否解释为什么在1>之前放置2>&1将无法实现预期的效果?我强烈怀疑这与"cmd"解析命令的方式有关,这些命令根据您指定重定向的顺序给出两种不同的含义.但是在任何地方都记录了语义规则,因为我认为这是值得学习的东西,因为它可能浪费数小时. (4认同)
  • @FrinkTheBrave但是如果没有明确指定,则流1是标准输出(例如控制台).这仍然没有解释它imho. (3认同)

Sto*_*wke 76

MSKB的背景信息

虽然这个问题的公认答案是正确的,但解释原因并没有多大帮助并不是很有效,而且由于语法不是很明确,我做了一个快速谷歌找出实际发生的事情.希望这些信息对其他人有所帮助,我在这里发布.

取自MS Support KB 110930.


来自MSKB110930

从命令提示符重定向错误消息:STDERR/STDOUT

摘要

使用">"符号重定向应用程序的输出时,错误消息仍会打印到屏幕上.这是因为错误消息通常发送到标准错误流而不是标准输出流.

控制台(命令提示符)应用程序或命令的输出通常发送到两个单独的流.常规输出发送到标准输出(STDOUT),错误消息发送到标准错误(STDERR).使用">"符号重定向控制台输出时,只是重定向STDOUT.为了重定向STDERR,您必须为重定向符号指定"2>".这将选择第二个输出流,即STDERR.

该命令dir file.xxx(file.xxx不存在的地方)将显示以下输出:

Volume in drive F is Candy Cane Volume Serial Number is 34EC-0876

File Not Found
Run Code Online (Sandbox Code Playgroud)

如果NUL使用输出将输出重定向到设备dir file.xxx > nul,您仍会看到输出的错误消息部分,如下所示:

File Not Found
Run Code Online (Sandbox Code Playgroud)

要(仅)将错误消息重定向到NUL,请使用以下命令:

dir file.xxx 2> nul
Run Code Online (Sandbox Code Playgroud)

或者,您可以将输出重定向到一个位置,将错误重定向到另一个位置.

dir file.xxx > output.msg 2> output.err
Run Code Online (Sandbox Code Playgroud)

您可以使用"&1"命令将错误和标准输出打印到单个文件,将STDERR的输出重定向到STDOUT,然后将STDOUT的输出发送到文件:

dir file.xxx 1> output.msg 2>&1
Run Code Online (Sandbox Code Playgroud)


Hen*_*ema 28

要将stdout和stderr添加到脚本的常规日志文件中:

dir >> a.txt 2>&1
Run Code Online (Sandbox Code Playgroud)

  • `>>`附加到`>`覆盖文件的文件. (7认同)

小智 12

正确,进程的文件句柄1是STDOUT,由1>或通过重定向>(1可以省略,按照惯例,命令解释器[cmd.exe]知道处理它).文件句柄2是STDERR,重定向2>.

请注意,如果您使用这些来制作日志文件,那么除非您将outut发送到_uniquely_named_(例如日期和时间戳)日志文件,否则如果您运行相同的过程两次,重定向将覆盖(替换)以前的日志文件.

>>(对于stdout或stderr)将追加不替换该文件.因此,您将获得一个累积日志文件,显示该过程的所有运行结果 - 通常更有用.

快乐的小道......


eri*_*icp 5

我刚刚将答案砍掉,因为@Anders刚刚发布了它,但是...

从Windows帮助中,我搜索了重定向(URL ms-its:C:\ WINDOWS \ Help \ ntcmds.chm :: / redirection.htm)。

您可能需要阅读>>和|。(烟斗)。


小智 5

但是,不能保证SDTOUT和的STDERR输出使用重定向合并语法按及时顺序逐行交织POSIX

如果应用程序使用缓冲输出,则可能会发生一个流的文本在缓冲区边界处插入另一个流的情况,该边界可能出现在文本行的中间。

对于这样的任务,专用的控制台输出记录器(即"StdOut/StdErr Logger"by 'LoRd MuldeR')可能更可靠。

请参阅:MuldeR 的开源项目