转义传递给unix程序的Windows路径中的反斜杠

时间:2011-11-01 04:31:59

标签: bash cygwin

我试图逃避cygwin中的反斜杠,但似乎几乎不可能 我尝试了很多东西,但没有一个正常工作..

  echo "C:\Users\Ted\Documents\Unix\Scripts" | xargs echo
  echo 'C:\Users\Ted\Documents\Unix\Scripts' | xargs echo

更具体地说,我需要获得一个命令,以便在没有bash的情况下接收输入 失去反斜杠字符。每次我试图传递一个论点, 反斜杠总是消失,破坏了我的输入。我不知道 我怎么能告诉它只是在输入上留下反斜杠。

我尝试了以下但似乎没有工作

  alias cyg0='cygpath '$*'  '
  alias cyg1='cygpath "$*"  '
  alias cyg2='cygpath "'$*'"'

  alias cyg3='cygpath '$@'  '
  alias cyg4='cygpath "$@"  '
  alias cyg5='cygpath "'$@'"'


  Ted@Machine01 ~
  $ cyg0 C:\Users\Ted\Music\Enigma
  C:UsersTedMusicEnigma

  Ted@Machine01 ~
  $ cyg1 C:\Users\Ted\Music\Enigma
  cygpath: can't convert empty path

  Ted@Machine01 ~
  $ cyg2 C:\Users\Ted\Music\Enigma
  cygpath: can't convert empty path

  Ted@Machine01 ~
  $ cyg3 C:\Users\Ted\Music\Enigma
  C:UsersTedMusicEnigma

  Ted@Machine01 ~
  $ cyg4 C:\Users\Ted\Music\Enigma
  C:UsersTedMusicEnigma

  Ted@Machine01 ~
  $ cyg5 C:\Users\Ted\Music\Enigma
  cygpath: can't convert empty path

顺便说一句,我希望能够在没有的情况下输入C:\ Users \ Ted \ Music \ Enigma 引号。其中一个别名在使用引号时有效。

泰德

6 个答案:

答案 0 :(得分:10)

请阅读bash(1)(man bash)中标题为QUOTING的部分。

在你的第一个例子中,

echo "C:\Users\Ted\Documents\Unix\Scripts" | xargs echo

shell解释(然后删除)双引号内的反斜杠,因此第一个echo命令只能看到字符串C:UsersTedDocumentsUnixScripts

在你的第二个例子中,

echo 'C:\Users\Ted\Documents\Unix\Scripts' | xargs echo

单引号正确保护反斜杠,正如您可以通过仅运行第一个echo命令看到的那样,没有| xargs echo

在所有剩下的例子中,

cyg0 C:\Users\Ted\Music\Enigma
cyg1 C:\Users\Ted\Music\Enigma
...

因为参数(C:\Users\Ted\Music\Enigma)是不加引号的,所以shell再次解释并删除反斜杠,然后命令(cyg0cyg1,...)才会看到它们。和...

  

我希望能够在没有引号的情况下输入C:\ Users \ Ted \ Music \ Enigma。

抱歉,无法完成。如果不将反斜杠放在单引号中,shell会将每个反斜杠解释为后面跟随的字符的引号,然后删除反斜杠。

您有几个选择:

  1. 在命令行中使用单引号来保护反斜杠:

    cyg4 'C:\Users\Ted\Music\Enigma'
    
  2. 分别引用每个反斜杠字符,例如加倍,例如

    cyg4 C:\\Users\\Ted\\Music\\Enigma
    
  3. 改为使用正斜杠:

    cyg4 C:/Users/Ted/Music/Enigma
    
  4. 选项3可能真的是您的最佳解决方案。不幸的是,反斜杠字符对于所有Unix shell来说只是一个非常特殊的字符,这在处理DOS / Windows路径时会引起很多引用麻烦。但是,广为人知的是,DOS / Windows也非常乐意使用正斜杠(/)作为路径分隔符。试试吧。

    注意:在你的几个cyg *函数中,只有cyg1和cyg4是正确的。其他人使用不正确的引用。 cyg1仅对一个参数有用,因为它将所有参数连接成一个带引号的字符串,而cyg4可以接受并将多个参数传递给cygpath。但是,由于cyg4只传递其引用的参数,因此它不会添加任何值;它与单纯的没什么不同。

    cygpath C:/Users/Ted/Music/Enigma
    
    祝你好运。

答案 1 :(得分:4)

从Windows资源管理器中读取粘贴到命令行的路径时,我遇到了类似的问题:

echo "Please enter path (copy n paste from Win-Explorer):"
read -r myWinPath;

“read -r xyz”命令(使用arg。“ - r”)不会解释粘贴路径中的单个反斜杠。

myNewCygwinPath=`cygpath -a $myWinPath`;
echo $myNewCygwinPath;

维托里奥

答案 2 :(得分:4)

有时候尝试使用所用程序的手册很有用:-)。来自man xargs

OPTIONS
   -0, --null
          Input items are terminated by a null character instead  of  by
          whitespace,  and the quotes and backslash are not special (ev-
          ery character is taken literally).  Disables the end  of  file
          string, which is treated like any other argument.  Useful when
          input items might contain white space, quote marks,  or  back-
          slashes.   The GNU find -print0 option produces input suitable
          for this mode.

这个选项确实保留了整条线路。尝试:

echo 'C:\Users\Ted\Documents\Unix\Scripts' | xargs -0 echo

“ - 0”适合你!

请注意,对于多个arg,您必须将参数置零,例如find ... -print0grep ... --null

答案 3 :(得分:2)

我认识到这个答案对于派对来说已经很晚了......但是我在遇到同样麻烦的时候偶然发现了这个问题。

我正在使用Cygwin安装中的'xargs' - 而且 - 我是从常规cmd.exe shell调用它。

对我来说,我只是使用了同样位于Cygwin文件夹中的tr实用程序:

dir /b /s /a *.txt | tr "\\" "/" | xargs ...

这完全解决了我的“斜线问题”。

答案 4 :(得分:1)

我遇到了同样的问题,当使用cygpath将c:\ dirname等文件名转换为unix时,我得到的是c:dirname,甚至是更奇怪的东西。

事实证明,我的问题是我使用的文件名是由用户输入的,我正在使用" read"命令。阅读,而不是cygpath,通过抛出反斜杠导致我的问题。 "读-r"解决了这个问题。

答案 5 :(得分:1)

尝试:

echo "C:\Users\Ted\Documents\Unix\Scripts" | xargs -0 echo
echo 'C:\Users\Ted\Documents\Unix\Scripts' | xargs -0 echo

xargs -0 选项说明(来自gnu.org):

"输入文件名由空字符而不是空格终止,并且任何引号和反斜杠字符都不被视为特殊字符(每个字符都是字面意思)。禁用文件字符串的结尾,该字符串与任何其他参数一样。"

OR

您也可以使用sed

来实现这一目标
echo "C:\Users\Ted\Documents\Unix\Scripts" | sed 's/\\/\\\\/g' | xargs echo
echo 'C:\Users\Ted\Documents\Unix\Scripts' | sed 's/\\/\\\\/g' | xargs echo

这会将所有单个\替换为双\\,然后再将其传递给xargs,然后将\\双重\剥离回s/string_to_replace/replace_with/g 1}},而不是单一到无的原始情况。

sed 是一种有用的流编辑器工具,可用于简单的文本替换。这是一个tutorial,有一些很好的例子。

替换语法如下:

g

  • sed 's/\\/\\\\/g'修饰符用于替换所有次出现。没有它,只会替换第一场比赛。
  • \中的额外反斜杠用于转义每个\\字符的特殊含义。因此,\为文字字符\\\\\\\\

对于没有引号,您必须使用\代替 echo C:\\Users\\Ted\\Documents\\Unix\\Scripts | xargs echo ,因为标记的答案显示。

{{1}}