为了账号安全,请及时绑定邮箱和手机立即绑定

如何在bat脚本中回显控制台输出并将其发送到文件?

如何在bat脚本中回显控制台输出并将其发送到文件?

繁花如伊 2019-11-25 10:34:07
我有一个执行任务的批处理脚本,并将输出发送到文本文件。有没有办法在控制台窗口上也显示输出?例如:c:\Windows>dir > windows-dir.txt有没有办法dir在控制台窗口中显示输出并将其输出到文本文件中?
查看完整描述

3 回答

?
忽然笑

TA贡献1806条经验 获得超5个赞

不,您不能使用纯重定向。

但是,您可以使用一些技巧(例如tee.bat)。


我尝试解释一下重定向。


使用> file或<file重定向十个流之一。

如果重定向是在命令之前还是之后,则这并不重要,因此这两行几乎相同。


dir > file.txt

> file.txt dir

在此示例中,重定向只是1>的快捷方式,这意味着将对流1(STDOUT)进行重定向。

因此,您可以在任何流之前添加数字,例如2> err.txt,也可以在一行中重定向多个流。


dir 1> files.txt 2> err.txt 3> nothing.txt

在此示例中,“标准输出”将进入files.txt,所有错误都将在err.txt中,stream3将进入nothing.txt(DIR不使用流3)。

Stream0是STDIN

Stream1是STDOUT Stream2

是STDERR

Stream3-9未使用


但是,如果您尝试多次重定向同一流,会发生什么情况?


dir > files.txt > two.txt

“只能有一个”,它永远是最后一个!

因此等于dir> two.txt


好的,还有一种可能,将一个流重定向到另一个流。


dir 1>files.txt 2>&1 

2>&1将stream2重定向到stream1,而1> files.txt将所有都重定向到files.txt。

这里的顺序很重要!


dir ... 1>nul 2>&1

dir ... 2>&1 1>nul

是不同的。第一个将所有(STDOUT和STDERR)重定向到NUL,

但是第二行将STDOUT重定向到NUL,将STDERR重定向到“空” STDOUT。


作为一个结论,很明显为什么OtávioDécio和andynormancx的示例无法正常工作。


command > file >&1

dir > file.txt >&2

两者都尝试将stream1重定向两次,但是“只能有一个”,并且始终是最后一个。

所以你得到


command 1>&1

dir 1>&2

并且在第一个示例中,不允许将stream1重定向到stream1(并且不是很有用)。


希望能帮助到你。


查看完整回答
反对 回复 2019-11-25
?
牛魔王的故事

TA贡献1830条经验 获得超3个赞

是的,有一种方法可以在控制台(屏幕)和文件中显示单个命令输出。使用您的示例,使用...


@ECHO OFF

FOR /F "tokens=*" %%I IN ('DIR') DO ECHO %%I & ECHO %%I>>windows-dir.txt

详细说明:


该FOR命令将命令或文本的输出解析为变量,可以多次引用该变量。


对于诸如的命令,请DIR /B用单引号引起来,如下例所示。将DIR /B文本替换为所需的命令。


FOR /F "tokens=*" %%I IN ('DIR /B') DO ECHO %%I & ECHO %%I>>FILE.TXT

要显示文本,请用双引号引起来,如下例所示。


FOR /F "tokens=*" %%I IN ("Find this text on console (screen) and in file") DO ECHO %%I & ECHO %%I>>FILE.TXT

...以及换行...


FOR /F "tokens=*" %%I IN ("Find this text on console (screen) and in file") DO (

  ECHO %%I & ECHO %%I>>FILE.TXT

)

如果您有时只希望在控制台(屏幕)上输出,而有时只希望将输出发送到文件,而有时又希望同时发送给两个文件,请使用变量指定FOR循环的“ DO”子句,如下所示%TOECHOWHERE%。


@ECHO OFF

FOR %%I IN (TRUE FALSE) DO (

  FOR %%J IN (TRUE FALSE) DO (

    SET TOSCREEN=%%I & SET TOFILE=%%J & CALL :Runit)

)

GOTO :Finish


:Runit

  REM Both TOSCREEN and TOFILE get assigned a trailing space in the FOR loops

  REM above when the FOR loops are evaluating the first item in the list,

  REM "TRUE".  So, the first value of TOSCREEN is "TRUE " (with a trailing

  REM space), the second value is "FALSE" (no trailing or leading space).

  REM Adding the ": =" text after "TOSCREEN" tells the command processor to

  REM remove all spaces from the value in the "TOSCREEN" variable.

  IF "%TOSCREEN: =%"=="TRUE" (

      IF "%TOFILE: =%"=="TRUE" (

          SET TEXT=On screen, and in "FILE.TXT"

          SET TOECHOWHERE="ECHO %%I & ECHO %%I>>FILE.TXT"

        ) ELSE (

          SET TEXT=On screen, not in "FILE.TXT"

          SET TOECHOWHERE="ECHO %%I"

      )

    ) ELSE (

      IF "%TOFILE: =%"=="TRUE" (

          SET TEXT=Not on screen, but in "FILE.TXT"

          SET TOECHOWHERE="ECHO %%I>>FILE.txt"

        ) ELSE (

          SET TEXT=Not on screen, nor in "FILE.TXT"

          SET TOECHOWHERE="ECHO %%I>NUL"

      )

  )

  FOR /F "tokens=*" %%I IN ("%TEXT%") DO %TOECHOWHERE:~1,-1%

GOTO :eof


:Finish

  ECHO Finished [this text to console (screen) only].

  PAUSE


查看完整回答
反对 回复 2019-11-25
  • 3 回答
  • 0 关注
  • 3235 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信