Regex 用于从文件类型中删除ASCII的awk脚本

Regex 用于从文件类型中删除ASCII的awk脚本,regex,scripting,sed,awk,Regex,Scripting,Sed,Awk,下面是一个简单的命令 file * | awk '/ASCII text/ {gsub(/:/,"",$1); print $1}' | xargs chmod -x 如图所示,我无法理解上述awk的用法。 它是如何工作的?我猜,但它看起来像是在提取file命令输出中:之前的部分(即文件名)。gsub部分将删除文件名中的:,因此类似foo.txt:ASCII text的内容将变成foo.txt ASCII text。然后,打印将打印以空格分隔的列表中的第一项(在本例中,文件名为foo.txt)

下面是一个简单的命令

file * | awk '/ASCII text/ {gsub(/:/,"",$1); print $1}' | xargs chmod -x
如图所示,我无法理解上述awk的用法。
它是如何工作的?

我猜,但它看起来像是在提取file命令输出中
之前的部分(即文件名)。gsub部分将删除文件名中的
,因此类似
foo.txt:ASCII text
的内容将变成
foo.txt ASCII text
。然后,打印将打印以空格分隔的列表中的第一项(在本例中,文件名为
foo.txt
)。chmod将使所有这些文件都不可执行


这看起来很乏味。在grepping之后只说
awk-F:'{print$1}'
可能更容易,而不是整个替换技巧。此外,如果文件名中有空格,则会中断

我猜,但它似乎是在提取file命令输出中
之前的部分(即文件名)。gsub部分将删除文件名中的
,因此类似
foo.txt:ASCII text
的内容将变成
foo.txt ASCII text
。然后,打印将打印以空格分隔的列表中的第一项(在本例中,文件名为
foo.txt
)。chmod将使所有这些文件都不可执行


这看起来很乏味。在grepping之后只说
awk-F:'{print$1}'
可能更容易,而不是整个替换技巧。此外,如果文件名中有空格,则会中断

它使用
文件
来确定每个文件的类型(内容),然后选择ASCII文本,并删除第一个冒号中的所有内容(假定冒号是文件名和文件类型之间的分隔符;当文件名中有冒号时,这是脆弱的;正如Noufel指出的,它也很难做到这一点),然后使用
xargs
批处理然后清除执行位。(这样做的通常原因是从Windows传输的文件,因为Windows没有执行位,所以所有文件通常都以Unix看到的执行位结束。)


空间上的破损是可修复的
xargs
理解引用。不过,我会在最后一个冒号而不是第一个冒号上断开,因为
文件的ASCII文本类型字符串中通常不包含冒号。

它使用
文件来确定每个文件的类型(内容),然后选择ASCII文本,并从第一个冒号中删除所有内容(假定它是文件名和文件类型之间的分隔符;当文件名中有冒号时,它很脆弱;正如Noufel指出的,它也很难做到这一点),然后使用
xargs
进行批处理,然后清除执行位。(这样做的通常原因是从Windows传输的文件,因为Windows没有执行位,所以所有文件通常都以Unix看到的执行位结束。)


空格的中断是可以修复的;
xargs
理解引号。不过,我会在最后一个冒号上中断,而不是第一个冒号,因为
文件的ASCII文本类型字符串中通常不包含冒号。

有一个删除的答案,它几乎可以避免文件名中的空格或冒号问题还有
文件的输出
。我已投票取消删除答案,但我将继续发布一些改进,并添加一些解释

file -0 * | awk -F '\0' '$2 ~ /ASCII text/ {print $1 "\0"}' | xargs -0 chmod -x
由于文件名中不允许使用空值,因此可以安全地将其用作分隔符。此管道中的每个步骤都使用空值。
file
输出空值,
awk
在输入中接受空值并输出,xargs在输入中接受空值。我还将匹配指定给description字段,这样就不会在perha中触发误报ps文件名类似“ASCII文本”,但实际上其内容并非如此的特殊情况

正如其他人所说,您发布的AWK命令与
文件
命令中包含“ASCII文本”的输出行相匹配。然后删除每个冒号(因为
gsub()
是全局替换)从字段1开始,该字段是以冒号空格分隔的文件名。如果文件名包含冒号或空格(或两个或多个空格),则可能会出现问题。文件名将被截断,
chmod
将失败,甚至可能在具有类似名称的文件上错误触发(例如,“foo bar”和“foo”都存在,“foo”不是ASCII文本文件,因此您不希望触碰它,但“foo-bar”会被截断为“foo”和“oops!”。空格存在潜在问题的原因是默认情况下,AWK会在空格和制表符上进行字段拆分

您发布的管道AWK部分的细分:

  • /ASCII text/{
    -用于匹配正则表达式的每一行
  • gsub(/:/,“”,$1);
    -对于第一个字段中的每个冒号(作为正则表达式),替换为空字符串
  • print$1}
    -打印修改后的第一个字段

有一个被删除的答案,它几乎可以避免文件名中的空格或冒号以及
文件的输出问题。我已经投票取消删除该答案,但我将继续发布一些改进,并添加一些解释

file -0 * | awk -F '\0' '$2 ~ /ASCII text/ {print $1 "\0"}' | xargs -0 chmod -x
由于文件名中不允许使用空值,因此可以安全地将其用作分隔符。此管道中的每个步骤都使用空值。
file
输出空值,
awk
在输入中接受空值并输出,xargs在输入中接受空值。我还将匹配指定给description字段,这样就不会在perha中触发误报ps文件名类似“ASCII文本”,但实际上其内容并非如此的特殊情况

正如其他人所说,您发布的AWK命令与
文件中包含“ASCII文本”的
命令的输出行相匹配。