디렉토리의 파일 유형에 대한 재귀 통계?


65

전환 프로젝트를 위해 웹 사이트 스크랩을 수행했습니다. 400 .html파일, 100 .gif등 의 파일 형식에 대한 통계를 만들고 싶습니다.이 작업을 수행 하는 가장 쉬운 방법은 무엇입니까? 재귀 적이어야합니다.

편집 : maxschelpzig가 게시 한 스크립트를 사용하여 스크랩 한 사이트의 아키텍처로 인해 몇 가지 문제가 있습니다. 일부 파일은 *.php?blah=blah&foo=bar다양한 인수를 가진 이름 이므로 모두 고유 한 것으로 간주합니다. 따라서 솔루션은 *.php*모두 같은 유형 으로 간주 해야합니다.

답변:


96

당신은 사용할 수 finduniq이에 대한 예 :

$ find . -type f | sed 's/.*\.//' | sort | uniq -c
   16 avi
   29 jpg
  136 mp3
    3 mp4

명령 설명

  • find 모든 파일 이름을 재귀 적으로 인쇄
  • sed 파일 확장명까지 모든 파일 이름에서 접두사를 삭제합니다.
  • uniq 정렬 된 입력을 가정
    • -c 히스토그램과 같은 계산을 수행합니다.

비슷한 스크립트가 있습니다. 간단하고 빠릅니다.
Rufo El Magufo

일부 파일은 *.php?blah=blah&foo=bar다양한 인수를 가진 이름 이므로 모두 고유 한 것으로 간주합니다. 찾도록 수정하려면 어떻게해야 *.php*합니까?
user394

3
다른 sed 표현을 사용하려고 할 수 있습니다.sed 's/^.*\(\.[a-zA-Z0-9][a-zA-Z0-9][a-zA-Z0-9]\).*$/\1/'
maxschlepzig

각 부분의 기능에 대해 설명해 주셔서 감사합니다. 비슷한 주제에 대한 많은 답변이이 부분을 건너 뜁니다. / learning-to-fish
MechEthan

1
프룬 변종 @ bela83은 단락 평가 에 의존 하므로 첫 번째 버전 find -name '.*' -prune -o -type f -print은 다음과 같이 평가됩니다. 디렉토리 항목이 일치 .*하면 프룬하고 그렇지 않으면 파일 인 경우 인쇄하십시오. CWD .*와도 일치 하기 때문에 .모든 것이 정리됩니다. 즉 find는 첫 번째 디렉토리로 내려 가지 않습니다. 아마도 2 살짜리 버전은 find다르게 행동 했었을 수도 있습니다. 어쨌든 find -name '.*' -not -name . -prune -o -type f -print이것을 수정하십시오.
maxschlepzig 2016 년

6

zsh로 :

print -rl -- **/?*.*(D.:e) | uniq -c |sort -n

패턴이 **/?*.* 반복적으로 현재의 모든 디렉토리의 확장자를 가진 파일 및 하위 디렉토리와 일치합니다. 글로브 규정이 D 하자 zsh트래버스도 숨겨진 디렉토리와 숨겨진 파일을 고려, .정규 파일을 선택합니다. 역사 수정은 단지 파일 확장자를 유지합니다. print -rl한 줄에 하나의 일치 항목을 인쇄합니다. uniq -c연속 된 동일한 항목을 계산합니다 (글로브 결과는 이미 정렬되어 있음). sort사용 횟수별로 확장 을 정렬 하기위한 마지막 호출 입니다.


5

이 one-liner는 상당히 강력한 방법으로 보입니다.

find . -type f -printf '%f\n' | sed -r -n 's/.+(\..*)$/\1/p' | sort | uniq -c

find . -type f -printf '%f\n'인쇄없는 디렉토리와 트리의 모든 일반 파일의 기본 이름. 그건있을 수 있습니다 디렉토리에 대해 걱정할 필요가 없습니다 .당신에 그들 년대를 sed정규식.

sed -r -n 's/.+(\..*)$/\1/p'단지의 확장으로 들어오는 파일 이름을 바꿉니다. 예를 들면, .somefile.ext이된다 .ext. .+정규식 의 이니셜 에 유의하십시오 . 이로 인해 확장자 앞에 적어도 하나의 문자가 필요 .합니다. 이렇게하면 파일 .gitignore이름에 이름이 전혀없고 확장자가 '.gitignore'(예 : 원하는 것)로 취급되지 않습니다. 그렇지 않은 경우, 교체 .+로모그래퍼 .*.

나머지 줄은 허용 된 답변에서 나온 것입니다.

편집 : 파레토 차트 형식 으로 멋지게 분류 된 히스토그램을 원한다면 다른 sort끝에 히스토그램을 추가하십시오 .

find . -type f -printf '%f\n' | sed -r -n 's/.+(\..*)$/\1/p' | sort | uniq -c | sort -bn

빌드 된 Linux 소스 트리의 샘플 출력 :

    1 .1992-1997
    1 .1994-2004
    1 .1995-2002
    1 .1996-2002
    1 .ac
    1 .act2000
    1 .AddingFirmware
    1 .AdvancedTopics
    [...]
 1445 .S
 2826 .o
 2919 .cmd
 3531 .txt
19290 .h
23480 .c

1

이 내용으로 ~/bin불리는 폴더에 bash 스크립트를 넣었습니다 exhist.

#!/bin/bash

for d in */ ; do
        echo $d
        find $d -type f | sed -r 's/.*\/([^\/]+)/\1/' | sed 's/^[^\.]*$//' | sed -r 's/.*(\.[^\.]+)$/\1/' | sort | uniq -c | sort -nr
#       files only      | keep filename only          | no ext -> '' ext   | keep part after . (i.e. ext) | count          | sort by count desc
done

어느 디렉토리에 있든 그냥 'exh'를 입력하고 탭을 자동 완성하면 다음과 같이 보입니다.

$ exhist
src/
      7 .java
      1 .txt
target/
     42 .html
     10 .class
      4 .jar
      3 .lst
      2 
      1 .xml
      1 .txt
      1 .properties
      1 .js
      1 .css

추신 : 물음표 후 부분을 트리밍하는 것은 아마도 마지막 명령 후 다른 sed 명령으로 간단하게 수행해야합니다 (시도하지 않았습니다). sed 's/\?.*//'

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.