doskey 中的 `^&` 和 `$T` 表现相似但不相同

`^&` and `$T` in doskey behave similar but not same

我想在cmd中打开一个文件并在Sublime Text的特定组中编辑它,所以我创建了一个这样的doskey

rem version 1, ^&
doskey st="path_to\Sublime Text 3\sublime_text" --command "focus_group { \"group\":  }" ^& "path_to\Sublime Text 3\sublime_text" 
rem version 2, $T
doskey st="path_to\Sublime Text 3\sublime_text" --command "focus_group { \"group\":  }" $T "path_to\Sublime Text 3\sublime_text" 

^&$T之前的命令将把ST集中到你想要的组</code>上,<code>^&$T之后的命令将打开文件</code></p> <p>然后在<code>cmd

>>> rem version 1, ^&
>>> st 0 test.py & rem press enter
>>>
----------------------------------
>>> rem version 2, $T
>>> st 0 test.py & rem press enter, one more prompt compare version 1
>>>
>>>

再试一次

rem alias.bat in C:\Windows\System32, work like alias in linux
doskey lscd1=dir ^& cd ..
doskey lscd2=dir $T cd ..

结果

path1\path2> lscd1
Volume in drive C is OS
 Volume Serial Number is DA7D-663C

 Directory of path2

11/24/2019  09:45 PM   0 test.py
path1>
---------------------------------
path1\path2> lscd2
Volume in drive C is OS
 Volume Serial Number is DA7D-663C

 Directory of path2

11/24/2019  09:45 PM   0 test.py
path1\path2>
path1>

$TDoc

$T or $t Separates commands. Use either of these special characters to separate commands when you create macros or type commands on the doskey command line. These special characters are equivalent to using the ampersand (&) on a command line.

我猜 ^& 是“escape the ampersand”,为什么这两个行为不同?

有趣,我以前从未注意到差异。

当使用 $T 时,宏分别向 cmd.exe 发出每个命令,每个命令都有自己的提示。然而,随后的命令并没有回显到屏幕上,所以看起来有点奇怪。

例如:

C:\test>doskey $T=echo command 1 $T echo command 2

C:\test>$T
command 1

C:\test>command 2

C:\test>

当您使用 ^& 时,doskey 将整个构造视为一次性传递给 cmd.exe 的单个命令,因此您不会收到任何额外提示。请注意,^ 在定义阶段被消耗,因此只有 & 存储在定义中,而不是 ^&.

C:\test>doskey amp=echo command 1 ^& echo command 2

C:\test>amp
command 1
command 2

C:\test>

如果在主要定义

前后添加echo offecho on,您可以获得$T输出看起来像^&
C:\test>doskey $T2=echo off $T echo command 1 $T echo command 2 $T echo on

C:\test>$T2
command 1
command 2

C:\test>

如果我要使用 doskey 宏,那么我更愿意使用 ^&。但我很少使用它们,因为它们有严重的局限性:

  • 它们在批处理脚本中使用时不执行
  • 它们与管道组合时不执行
  • 它们在与 FOR /F %A in ('macro') do ...
  • 一起使用时不执行
  • 它们在与任何串联运算符 &&&||
  • 组合时不会执行

更新

当我说 $T 导致每个命令都有自己的提示时,这意味着每个命令都被单独解析。这有一个潜在的优势,因为您的宏可以设置变量 var,然后稍后访问值 %var%,而无需使用延迟扩展。当使用 ^& 时,所有命令都被一次解析,所以你不能使用 %var%.

这是一个愚蠢的例子,说明如何不能将 %v%^& 一起使用,但可以将 %v%$T

一起使用
C:\test>set "v="

C:\test>doskey m1=set "v=OK" ^& echo v=%v% - doesn't work with ^^^^^^^& ^& set "v="

C:\test>m1
v=%v% - doesn't work with ^&

C:\test>doskey m2=set "v=OK" $T echo v=%v% - works with $^^T $T set "v="

C:\test>m2

C:\test>v=OK - works with $T

C:\test>

一个更实际的例子是一个执行命令然后根据结果执行某些操作的宏 %errorlevel%