find
로 원하는 파일을 찾아보자! (2)¶
이번 시간에는 find
의 표현식
중에서 연산자
, 액션
, 위치옵션
이 무엇인지 알아보겠습니다.
시작하기 전에 지난 시간에 배운 find
의 기본적인 사용법과 표현식
에 대해 간단하게 복습해볼까요?
find
는 파일을 탐색할 때 사용하는 명령어이며 find [옵션] [대상경로] [표현식]
의 형태로 사용합니다.
이 중 표현식은 파일을 탐색할 조건들을 의미합니다.
표현식의 종류는 4가지로 테스트, 연산자, 액션, 위치옵션이 있는데, 이러한 표현식들을 조합해서 원하는 파일을 탐색할 수 있습니다.
지난 글에서는 이 중 하나인 테스트
에 대해서 공부했습니다.
테스트는 파일을 탐색하는 기준
을 정의하는 역할을 하며 기준
으로 정할 수 있는 항목은 파일명
, 권한
, 생성 및 변경시간
등이 있습니다.
이번 글에서는 테스트
의 결과로 연산을 하는 연산자
, 표현식의 결과를 활용해서 다른 명령어를 실행하는 액션
그리고 테스트
의 수행 방법에 영향을 주는 위치옵션
에 대해서 알아보겠습니다.
이번에 실습할 디렉터리의 구조는 아래와 같습니다.
$ tree ./
./
├── File
│ ├── File
│ ├── express.txt -> ../expression.txt
│ ├── file1.txt
│ ├── file2.txt
│ └── test.txt
├── Separator.txt
├── aa.txt
├── amin.txt
├── bb.txt
├── expression.tar.gz
├── expression.txt
├── findtestfile
├── grep-test
├── pattern
│ ├── findtestfile
│ ├── pattern1.txt
│ ├── pattern2.txt
│ └── pattern3.txt
└── test.txt
참고로 위와 같이 트리형태로 파일목록을 출력하고 싶을 때는 tree
명령어를 사용하면 됩니다.
명령어를 찾을 수 없는 경우 yum
, brew
같은 패키지매니저를 통해 tree
패키지를 설치해주면됩니다.
e.g.) yum install tree
, brew install tree
...
1. 연산자¶
연산자는 표현식의 결과를 연산할 때 사용합니다.
연산자의 종류로는 and
, or
, not
등이 있습니다.
논리연산자를 사용해본 경험이 있다면 각 연산자의 실행 결과를 쉽게 예상할 수 있을 것이라 생각됩니다.
그럼 각 연산자를 어떻게 사용하는지 알아보겠습니다.
1.1 AND¶
- 표현식1 표현식2
- 표현식1 -a 표현식2
- 표현식1 -and 표현식2
$ find ./ -type f -name 'p*'
./pattern/pattern1.txt
./pattern/pattern2.txt
./pattern/pattern3.txt
$ find ./ -type f -a -name 'p*'
./pattern/pattern1.txt
./pattern/pattern2.txt
./pattern/pattern3.txt
$ find ./ -type f -and -name 'p*'
./pattern/pattern1.txt
./pattern/pattern2.txt
./pattern/pattern3.txt
AND연산은 위 처럼 3가지 형태로 수행할 수 있습니다.
논리연산자 AND(&)와 마찬가지로 표현식1, 2를 모두 만족하는 대상만 결과에 포함합니다.
1.2 OR¶
- 표현식1 -o 표현식2
- 표현식1 -or 표현식2
$ find ./ -type d -o -name 'a*'
./
./pattern
./aa.txt
./amin.txt
./File
$ find ./ -type d -or -name 'a*'
./
./pattern
./aa.txt
./amin.txt
./File
OR 연산은 위 2가지 형태로 사용합니다.
논리연산자 OR(|)와 마찬가지로 표현식1, 2중 하나만 만족하면 결과에 포함합니다.
1.3 NOT¶
- ! 표현식
- -not 표현식
$ find ./ ! -type f
./
./pattern
./File
./File/express.txt
$ find ./ -not -type f
./
./pattern
./File
./File/express.txt
NOT 연산은 위 2가지 형태로 사용합니다.
앞서 살펴본 AND, OR와는 다르게 단항연산자이며 표현식의 앞에 위치하며, 표현식을 만족하지 않는 대상만을 결과에 포함합니다.
1.4 (,)¶
- 표현식1 , 표현식2 , 표현식3 ...
$ find ./ -name 'a*' , -name 'b*'
./bb.txt
$ find ./ \( -name 'a*' -printf '%p\n' \) , \( -name 'b*' -printf '%p\n' \)
./aa.txt
./bb.txt
./amin.txt
콤마 연산자는 여러개의 표현식을 실행할 때 사용됩니다.
실행 결과는 제일 마지막 표현식의 결과만 보여주는데, 표현식의 실행 결과를 모두 확인하기 위해서는 위 예시의 2번째 명령어 처럼 각각 -print
액션을 사용해야 합니다.
-print
는 뒤에서 액션을 소개할 때 자세히 다루도록 하겠습니다.
1.5 () 연산자¶
- ( 표현식 )
$ find ./ -name 'a*' -print , -name 'b*' -print
./txtdir/aa.txt
./txtdir/bb.txt
./txtdir/amin.txt
$ find ./ \( -name 'a*' -print \) , \( -name 'b*' -print \)
./txtdir/aa.txt
./txtdir/bb.txt
./txtdir/amin.txt
소괄호 연산자는 표현식의 우선순위를 정의하거나 그룹핑을 해야하는 경우 사용합니다.
위 예시를 보면 소괄호 연산자를 사용했을 때 결과를 출력하는 순서가 다른 점을 알 수 있습니다.
주의사항으로는 반드시 괄호 앞에 역슬래시(\)
를 사용해야한다는 점이 있습니다.
2. 액션¶
액션은 테스트와 같은 표현식의 결과를 인자로 받아 다른 처리를 해야할 때 사용합니다.
액션의 종류는 크게 명령어 실행 관련 액션
, 결과 출력 관련 액션
2가지로 나눌 수 있습니다.
명령어 실행 관련 액션
은 표현식의 결과를 인자로 받아서 명령어를 수행하고 싶을 때 사용합니다.
결과 출력 관련 액션
은 표현식의 결과를 인자로 받아서 원하는 방식으로 출력하고 싶을 때 사용합니다.
액션의 종류는 다양하기 때문에 이번 시간에는 종류별로 실용적이라 생각되는 액션들만 다뤄보겠습니다.
그럼 먼저 명령어 실행 관련 액션
부터 알아보겠습니다.
2.1 명령어 실행 관련 액션¶
명령어 실행 관련 액션의 대표적인 액션으로는 -exec
가 있습니다.
사용하는 방법은 테스트의 뒤에 -exec 명령어{} \;
또는 -exec 명령어{} +;
와 같이 사용하며, 중괄호({})
에는 인자로 받은 표현식의 결과가 들어오게 됩니다.
앞서 소개한 사용 방법에서 명령어 뒤에 끝맺음을 할 때 세미콜론(;)
과 플러스(+)
를 사용하는것을 보셨을텐데요.
세미콜론(;)
은 결과값을 줄바꿈해서 보여주고 역슬래시와 함께 사용해야하는 반면 플러스(+)
는 결과값들을 이어서 보여준다는 차이점이 있습니다.
아래의 예시 코드에서 차이점을 확인할 수 있는데요, echo
는 문자열을 받아서 터미널에 출력하는 명령어입니다.
;
와 +
의 실행 결과에 차이가 있는 것을 확인할 수 있습니다.
$ find ./ -name 'a*' -exec echo '{}' \;
./aa.txt
./amin.txt
$ find ./ -name 'a*' -exec echo '{}' +
./aa.txt ./amin.txt
조금 더 복잡한 예시를 살펴볼까요?
현재의 파일목록에서 확장자가 txt
인 파일들을 txtdir
이라는 디렉터리에 모으려고 합니다.
-exec
를 활용하면 아래처럼 쉽게 처리할 수 있습니다!
참고로 파이프(|)
를 사용하면 명령어를 이어서 실행할 수 있습니다.
$ mkdir txtdir | find ./ -name '*.txt' -exec mv {} txtdir \;
$ tree ./
./
├── File
│ └── File
├── expression.tar.gz
├── findtestfile
├── grep-test
├── pattern
│ └── findtestfile
└── txtdir
├── Separator.txt
├── aa.txt
├── amin.txt
├── bb.txt
├── express.txt -> ../expression.txt
├── expression.txt
├── file1.txt
├── file2.txt
├── pattern1.txt
├── pattern2.txt
├── pattern3.txt
└── test.txt
3 directories, 17 files
2.2 결과 출력 관련 액션¶
결과 출력 관련 액션
은 검색된 파일들을 원하는 포맷으로 출력하거나 검색 결과를 파일에 저장할 때 사용합니다.
액션으로는 -print
, -ls
, -fprint 파일
, -fls 파일
이 있습니다.
-print
와 -ls
는 검색된 파일들을 터미널에 보여줍니다.
각 액션의 차이점은 -print
는 파일들을 ls
의 포맷으로 보여주고 -ls
는 ls -l
의 출력 결과처럼 보여줍니다.
-fprint 파일
과 -fls 파일
은 각각 위 액션의 실행 결과를 파일로 저장합니다.
이 외에도 -printf
, -fprintf
등의 명령어가 있는데, 프로그래밍 언어의 printf
처럼 원하는 포맷으로 출력할 수도 있습니다.
$ find ./ -name 'a*' -print
./txtdir/aa.txt
./txtdir/amin.txt
$ find ./ -name 'a*' -ls
1516989 68 -rw-rw---- 1 centos centos 65942 5월 15 2020 ./txtdir/aa.txt
1516991 4 -rw------- 1 centos centos 30 5월 19 2020 ./txtdir/amin.txt
$ find ./ -name 'a*' -fprint f-file.txt
$ cat f-file.txt
./txtdir/aa.txt
./txtdir/amin.txt
$ find ./ -name 'a*' -fls fls-file.txt
$ cat fls-file.txt
1516989 68 -rw-rw---- 1 centos centos 65942 5월 15 2020 ./txtdir/aa.txt
1516991 4 -rw------- 1 centos centos 30 5월 19 2020 ./txtdir/amin.txt
3. 위치옵션¶
일반적으로 위치옵션
은 테스트
의 수행 방법에 영향을 줍니다.
몇몇의 옵션을 제외하고는 테스트보다 먼저오나 나중에오나 항상 먼저 실행된다는 특징이 있습니다.
때문에 가독성을 위해서라도 옵션을 앞에 정의하는것이 좋습니다.
탐색 범위에서 CD-ROM
, USB
같은 외부 장치를 제외하는 -mount
, 하위 디렉터리 깊이를 제한하는 -maxdepth 깊이
등이 있습니다.
이 중에서는 확인이 수월한 -maxdepth 깊이
에 대해서 살펴 보겠습니다.
3.1 maxdepth¶
$ find ./ -name 'p*'
./pattern
./txtdir/pattern1.txt
./txtdir/pattern2.txt
./txtdir/pattern3.txt
$ find ./ -maxdepth 1 -name 'p*'
./pattern
$ find ./ -maxdepth 2 -name 'p*'
./pattern
./txtdir/pattern1.txt
./txtdir/pattern2.txt
./txtdir/pattern3.txt
위 코드는 -maxdepth
의 실행 결과를 비교한 내용입니다.
위치옵션을 사용하지 않으면 기본적으로 모든 하위 디렉터리를 대상으로 탐색합니다.
-maxdepth 1
의 경우 현재 디렉터리에서만 탐색을 하는 반면 -maxdepth 2
는 바로 하위 디렉터리까지 탐색을 하는 것을 확인할 수 있습니다.
마무리¶
이번에는 표현식에 속하는 연산자
, 액션
, 위치옵션
에 대해서 알아보았습니다.
지금까지 알아본 표현식에 대한 이해만으로도 find
를 활용하기에 충분하다고 생각합니다만, 짚고 넘어가지 않은 내용에 옵션이라는 기능이 있습니다.
옵션
의 활용 방법에는 여러가지가 있는데 대표적으로는 find
의 탐색 대상에서 심볼릭 링크
파일은 어떻게 처리할 것인지에 대해 정의할 때 사용합니다.
이 부분에 대해서는 파일시스템의 링크
에 대한 이해를 필요로합니다.
그래서 다음 글에서는 간단하게 링크
란 무엇인지 먼저 알아보고 옵션
에 대해서 가볍게 다뤄볼 예정입니다.
참고¶
- 처음 배우는 셸 스크립트 - 한빛미디어
작성자: 성승익
작성일: 2021-09-21