"찾기"결과를 계산하는 가장 좋은 방법은 무엇입니까?


99

내 현재 솔루션은 find <expr> -exec printf '.' \; | wc -c이지만 10000 개 이상의 결과가있는 경우 너무 오래 걸립니다. 이 작업을 수행하는 더 빠르고 더 나은 방법이 없습니까?


귀하의 찾기 결과에 화장실 -l을 사용
마누엘 셀바

답변:


84

대신 이것을 시도하십시오 ( find-printf지원 필요 ) :

find <expr> -type f -printf '.' | wc -c

줄을 세는 것보다 더 안정적이고 빠릅니다.

외부 명령이 아닌 find's를 사용합니다 printf.


벤치를 조금 보자.

$ ls -1
a
e
l
ll.sh
r
t
y
z

내 스 니펫 벤치 마크 :

$ time find -type f -printf '.' | wc -c
8

real    0m0.004s
user    0m0.000s
sys     0m0.007s

전체 라인 :

$ time find -type f | wc -l
8

real    0m0.006s
user    0m0.003s
sys     0m0.000s

그래서 내 솔루션은 더 빠릅니다 =) (중요한 부분은 real라인입니다)


6
동일하지, 그것은) = 더 안정적이다
질 Quenot

6
찾을 -printf 플래그가 플랫폼에서 지원되지 않는 경우 더 안정적이지 않습니다. ;-)
Randy Howard

7
당신이하지에있는 점을 인용하여 몇 나노초를 면도 할 수 있습니다-printf '.'
옌스

6
@Jens은 - 특히 당신의 계정에 그를 입력하는 데 걸리는 시간을 때
브라이언 애그뉴에게

6
이러한 작은 벤치 마크를 사용하면 측정하려는 항목이 아닌 다른 요소가 타이밍을 지배 할 수 있습니다. 큰 나무를 사용한 실험이 더 유용 할 것입니다. 그러나 이것은 OP가 요청한 것을 실제로 수행하는 것에 대한 나의 투표를 얻습니다.
tripleee

133

왜 안돼

find <expr> | wc -l

간단한 휴대용 솔루션으로? 원래 솔루션은 발견 된 모든 개별 파일에 대해 새로운 프로세스 printf생성하고 있으며, 이는 매우 비쌉니다 (방금 찾은대로).

줄 바꿈이 포함 된 파일 이름이 있으면이 값이 과도하게 계산되지만 그게 있으면 문제가 조금 더 깊어 질 것 같습니다.


9
-1 : 것 개행 문자와 파일에 휴식, 그리고보다 느리다 바이트 =) 계산
질 Quenot

21
나는 돈, t는 보증 파일 이름 / 줄 바꿈 제한은 매우 드문 것으로 주어진 downvote 생각 하고 위에서 언급. 천천히? 혹시. 파일 시스템을 쿼리하는 경우 속도 차이가 작다고 생각합니다. 10,000 개의 파일에서 3ms 차이를 측정합니다
Brian Agnew 2013 년

8
'find <expr> | wc -l'및 'find <expr> -printf 간의 성능 차이. | wc -c '는 매우 작습니다. 캐싱 (즉, 동일한 트리에서 동일한 찾기를 두 번 실행하는 경우)이 훨씬 더 중요합니다. IMHO 솔루션은 "wc -l"이 훨씬 더 직관적입니다.
pitseeker

4

이것은 내 countfiles기능입니다 ~/.bashrc(합리적으로 빠르며 Linux 및 FreeBSD find에서 작동해야하며 줄 바꿈 문자를 포함하는 파일 경로에 속지 않습니다. 마지막 wc은 NUL 바이트를 계산합니다) :

countfiles () 
{ 
   command find "${1:-.}" -type f -name "${2:-*}" -print0 | 
       command tr -dc '\0' | command wc -c;
return 0
}

countfiles

countfiles ~ '*.txt'

4

이 솔루션은 find -> wc여기 에있는 다른 솔루션 보다 확실히 느리지 만 파일 이름을 계산하는 것 외에도 파일 이름으로 다른 작업을 수행하려는 경우 출력 read에서 할 수 있습니다 find.

n=0
while read -r -d ''; do
    ((n++)) # count
    # maybe perform another act on file
done < <(find <expr> -print0)
echo $n

를 사용하여 출력 구분 기호를 NUL 바이트 로 만들고 루프 구분 기호로 (NUL 바이트)를 사용하여 읽음으로써 비표준 이름을 가진 파일을 올바르게 처리하는 BashGuide에서 발견 된 솔루션의 수정일뿐입니다 .findprint0''

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