代码之家  ›  专栏  ›  技术社区  ›  Joseph Lust

带有Xargs的Sed无法打开传递的文件(Cygwin)

  •  1
  • Joseph Lust  · 技术社区  · 11 年前

    尝试使用Sed的美丽,这样我就不必手动更新几百个文件。我会注意到我的雇主只允许使用Win8(joy),所以我整天都在使用Cygwin,直到我可以在家里使用我的Linux系统。

    以下命令在Linux(bash)命令行上运行,但不适用于Cygwin

    > grep -lrZ "/somefile.js" . | xargs -0 -l sed -i -e 's|/somefile.js|/newLib.js|g'
    sed: can't read ./testTarget.jsp: No such file or directory
    
    # works
    > sed -i 's|/somefile.js|/newLib.js|g' ./testTarget.jsp
    

    因此,命令本身有效,但未通过Xargs传递。而且,在您说使用Perl而不是Sed之前,Perl等价物会抛出同样的错误

    > grep -lrZ "/somefile.js" . | xargs -0 perl -i -pe 's|/somefile.js|/newLib.js|g'
    Can't open ./testTarget.jsp
    : No such file or directory.
    
    1 回复  |  直到 11 年前
        1
  •  0
  •   Matthew    10 年前

    使用 xargs -n 选项分割参数并强制单独调用sed。

    在使用GnuWin工具(而不是Cygwin)的windows上,我发现需要将输入拆分为sed。默认情况下,xargs会将grep中的所有文件传递给sed的一个调用。

    假设您有4个与grep调用匹配的文件,sed命令将通过xargs运行,如下所示:

    sed -i -e 's|/somefile.js|/newLib.js|g' ./file1 ./file2 ./subdir/file3 ./subdir/file4
    

    如果文件的数量太大,sed会给你这个错误。 使用-n选项反复调用xargs,直到它耗尽所有参数。

    grep -lrZ "/somefile.js" . | xargs -0 -l -n 2 sed -i -e 's|/somefile.js|/newLib.js|g'
    

    在我的小示例中,使用-n 2将在内部执行以下操作:

    sed -i -e 's|/somefile.js|/newLib.js|g' ./file1 ./file2 
    sed -i -e 's|/somefile.js|/newLib.js|g' ./subdir/file3 ./subdir/file4
    

    我有一大堆文件和目录(大约3000个文件),使用xargs-n5效果很好。 当我尝试-n 10时,我遇到了错误。使用xargs-verbose,我可以看到一些命令行调用在大约500个字符处被截断。因此,您可能需要根据正在处理的文件的路径长度来减小-n。