在 Linux 机器上,我想遍历文件夹层次结构并获取其中所有不同文件扩展名的列表。

从 shell 实现此目的的最佳方法是什么?

有帮助吗?

解决方案

试试这样(不知道如果这是最好的方式,但它的工作):

find . -type f | perl -ne 'print $1 if m/\.([^.\/]+)$/' | sort -u

它的工作如下:

  • 找到的所有文件从前文件夹
  • 印扩展的文件,如果任何
  • 做一个独特的序列表

其他提示

没有需要对管sort,AWK可以做到这一切:

find . -type f | awk -F. '!a[$NF]++{print $NF}'

递归版本:

find . -type f | sed -e 's/.*\.//' | sed -e 's/.*\///' | sort -u

如果您想要总数(扩展被看到的次数):

find . -type f | sed -e 's/.*\.//' | sed -e 's/.*\///' | sort | uniq -c | sort -rn

非递归(单个文件夹):

for f in *.*; do printf "%s\n" "${f##*.}"; done | sort -u

我基于此 这个论坛帖子, ,信用应该去那里。

Powershell的:

dir -recurse | select-object extension -unique

由于 http://kevin-berridge.blogspot.com/一十一分之二千零七/窗口-powershell.html

找到与一个点的everythin,仅显示后缀。

find . -type f -name "*.*" | awk -F. '{print $NF}' | sort -u

如果你知道所有后缀有3个字符,那么

find . -type f -name "*.???" | awk -F. '{print $NF}' | sort -u

或具有SED示出了具有一至四个字符的所有后缀。变化{1,4}的字符你期待在后缀。的范围

find . -type f | sed -n 's/.*\.\(.\{1,4\}\)$/\1/p'| sort -u

添加我自己的变化的组合。我认为这是最简单的的很多,当效率是不是一个大问题是有用的。

find . -type f | grep -o -E '\.[^\.]+$' | sort -u

我AWK-以下,sed的少,Perl的少,Python的少POSIX兼容的替代:

find . -type f | rev | cut -d. -f1 | rev  | tr '[:upper:]' '[:lower:]' | sort | uniq --count | sort -rn

诀窍在于,它反转线并切割在开始扩展。结果 它还扩展转换为小写。

输出示例:

   3689 jpg
   1036 png
    610 mp4
     90 webm
     90 mkv
     57 mov
     12 avi
     10 txt
      3 zip
      2 ogv
      1 xcf
      1 trashinfo
      1 sh
      1 m4v
      1 jpeg
      1 ini
      1 gqv
      1 gcs
      1 dv

在使用Python生成对于非常大的目录,包括空白扩展,并获得的次数每个扩展显示出来:

import json
import collections
import itertools
import os

root = '/home/andres'
files = itertools.chain.from_iterable((
    files for _,_,files in os.walk(root)
    ))
counter = collections.Counter(
    (os.path.splitext(file_)[1] for file_ in files)
)
print json.dumps(counter, indent=2)

我尝试了一堆问题的答案在这里,即使是"最好"的回答。他们都来了短什么我具体是之后。因此,除了过去12个小时坐在regex代码,用于多个项目和阅读和测试这些答案,这是什么我想到了与其工作完全像我想要的。

 find . -type f -name "*.*" | grep -o -E "\.[^\.]+$" | grep -o -E "[[:alpha:]]{2,16}" | awk '{print tolower($0)}' | sort -u
  • 发现的所有文件,这些文件可能具有扩展。
  • Greps仅延伸
  • Greps文件的扩展之间2和16个字符的(只是调整数字,如果他们不适合你的需要).这有助于避免缓存文件的文件和系统文件(文件系统位于搜索监狱).
  • Awk打印的扩展低的情况。
  • 排序,并把在只有独特的价值观。最初我尝试尝试awk的答案,但它将打印的项目,在变化的情况的敏感性。

如果你需要一个计数的文件的扩展,然后使用以下的代码

find . -type f -name "*.*" | grep -o -E "\.[^\.]+$" | grep -o -E "[[:alpha:]]{2,16}" | awk '{print tolower($0)}' | sort | uniq -c | sort -rn

虽然这些方法将需要一些时间来完成,并可能不是最好的方式去有关的问题,他们的工作。

更新:每@alpha_989长文件的扩展将导致一个问题。这是由于原regex"[[:alpha:]]{3,6}".我已经更新的答案,包括regex"[[:alpha:]]{2、16的}".但是任何人使用这个代码应该认识到,这些数字是最小和最大的多长时间的延长是最终的输出。什么外面,范围将被分割为多个行在的输出。

注:原来的职位有没有读"-Greps文件的扩展之间3和6个字符的(只是调整数字,如果他们不适合你的需要).这有助于避免缓存文件的文件和系统文件(文件系统位于搜索监狱)."

想法:可用于查找的文件的扩展在一个特定长度,通过:

 find . -type f -name "*.*" | grep -o -E "\.[^\.]+$" | grep -o -E "[[:alpha:]]{4,}" | awk '{print tolower($0)}' | sort -u

其中4个是文件,延长到包括然后发现的任何扩展超过长度。

由于已经有其使用Perl另一种解决方案:

如果您已经安装了Python,你也可以这样做(从shell):

python -c "import os;e=set();[[e.add(os.path.splitext(f)[-1]) for f in fn]for _,_,fn in os.walk('/home')];print '\n'.join(e)"

答复的无迄今处理与正确的换行符(除了ChristopheD的,这刚进来的,因为我是打字)的文件名。以下是不是一个壳状的衬垫,但工程,并且是相当快的。

import os, sys

def names(roots):
    for root in roots:
        for a, b, basenames in os.walk(root):
            for basename in basenames:
                yield basename

sufs = set(os.path.splitext(x)[1] for x in names(sys.argv[1:]))
for suf in sufs:
    if suf:
        print suf

我不认为这是一个尚未提到的:

find . -type f -exec sh -c 'echo "${0##*.}"' {} \; | sort | uniq -c

我认为最简单&直接的方法是

for f in *.*; do echo "${f##*.}"; done | sort -u

它改性上ChristopheD的第三方式。

您也可以做到这一点。

find . -type f -name "*.php" -exec PATHTOAPP {} +
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top