我试图使用sed命令计算基于特定扩展名的所有行数。
find -name '*.m' -exec wc -l {} \; | sed ...
我试图做以下操作,请问如何在这行代码中使用sed获取总数。您也可以使用 wc 命令获得漂亮的格式化输出:
wc `find -name '*.m'`
这里大多数答案无法很好地处理大量文件。一些解决方案在单个命令行调用的文件名列表太长时会出现错误,而其他解决方案效率低下,因为-exec
会为每个文件启动一个新进程。我认为一个强大且高效的解决方案应该是:
find . -type f -name "*.m" -print0 | xargs -0 cat | wc -l
这种方式使用cat
是可以的,因为它的输出被直接管道到wc
中,所以每次只会在内存中保留少量文件内容。如果有太多的文件需要进行单个cat
调用,则会多次调用cat
,但所有输出仍将被输送到单个wc
进程中。
find . -type f -name '*.m' -exec cat {} + | wc -l
。 - Stephane Chazelas-exec wc -l {} +
而不是-print0 | xargs ...
。使用+
与-exec
可能会运行多个wc -l
实例,然后您需要对每次运行的总计进行求和以获得总体总数。或者,如果您不关心总数,请使用grep -v
删除那些行;或者,使用-exec wc -l {} \;
在每个文件上运行单独的wc
实例,但处理成本略高。 - tripleeewc
实例将所有文件连接起来,以获得总行数:cat
find . -name '*.m' -exec cat {} \; | wc -l
在现代GNU平台上,wc和find命令可以使用-print0和-files0-from参数组合成一个命令,该命令可以计算文件中的行数,并在末尾显示总数。示例:
find . -name '*.c' -type f -print0 | wc -l --files0-from=-
您也可以使用sed来计算行数,而不是使用wc:
find . -name '*.m' -exec sed -n '$=' {} \;
其中'$='
是一个“特殊变量”,用于计算行数
编辑
您还可以尝试类似sloccount的工具。
嗯,如果您有许多文件,尤其是大文件,则使用cat解决方案可能会出现问题。
第二种解决方案只提供每个文件的行数,无法给出总行数,我已经测试过了。
我更喜欢像这样的解决方案:
find . -name '*.m' | xargs wc -l | tail -1
sed 不是计数的合适工具。请使用 awk 代替:
find . -name '*.m' -exec awk '{print NR}' {} +
使用 + 而不是 \; 强制 find 每找到 N 个文件就调用 awk(就像 xargs 一样)。
对于大型目录,我们应该使用:
find . -type f -name '*.m' -exec sed -n '$=' '{}' + 2>/dev/null | awk '{ total+=$1 }END{print total}'
# alternative using awk twice
find . -type f -name '*.m' -exec awk 'END {print NR}' '{}' + 2>/dev/null | awk '{ total+=$1 }END{print total}'
wc $(find -type f -name '*.m')
。该命令的作用是找到所有扩展名为“.m”的文件,并将它们传递给“wc”命令计算它们的行数、单词数和字符数。 - Dennis Williamsonfind . -name '*.m' -exec wc {} \;
。 - Working dollar