bash script2023. 10. 10. 21:32

 

반달가면 이글루에서 백업 - http://bahndal.egloos.com/625366

csplit은 리눅스에서 기본적으로 제공되는 파일 분할 프로그램이다. 특정 행번호, 또는 특정 문자열을 기준으로 파일을 분할해야 하는 경우에 사용한다.

csplit의 인자(argument)는 아래와 같이 지정한다

csplit [옵션] [입력 파일] [패턴]

자주 사용하는 옵션은 아래와 같다.

-f: 분할된 출력 파일 이름 지정
-z: 결과중에 크기가 0인 파일은 삭제
-k: 오류가 발생할 경우에도 이전까지 생성된 분할 결과 파일 유지(-k 옵션이 없으면 오류 발생시 출력 결과가 삭제된다.)

패턴은 행번호 또는 정규표현식(regular expression, regex), 그리고 반복 회수를 지정할 수 있다. 몇가지 예시를 통해서 살펴보자.

예시에 사용할 파일 sample.txt의 내용은 아래와 같다고 가정한다.

# 예시용 파일 내용 확인
cat sample.txt
1 apple
2 orange
3 pineapple
4 banana
5 cherry
6 apple
7 orange
8 pineapple

우선 행번호의 경우 첫번째 행부터 지정한 행 바로 전 행까지를 하나의 파일로, 나머지를 또 하나의 파일로 분할할 수 있다. 아래의 예시를 보자.

# 첫번째행부터 4번째 행까지 1개 파일, 나머지를 1개 파일로 분리, 분할 결과 파일명은 "output"으로 시작
csplit -f "output" sample.txt 5

# 결과 확인
cat output00
1 apple
2 orange
3 pieapple
4 banana

cat output01
5 cherry
6 apple
7 orange
8 pineapple

개인적으로 요긴하게 사용하는 방식은 정규표현식을 이용해서 특정한 문자열을 경계선으로 하여 분할하는 방식이다. 아래의 예시를 보자. 입력 파일의 마지막에 도달할 때까지 반복하기 위해 '{*}' 패턴을 인자로 사용했다.

# 문자열 "apple"이 포함된 행을 기준으로 반복 분할, 분할 결과 파일명은 "output"으로 시작
csplit -f "output" sample.txt '/apple/' '{*}'

# 결과 확인
cat output00

cat output01
1 apple
2 orange

cat output02
3 pineapple
4 banana
5 cherry

cat output03
6 apple
7 orange

cat output04
8 pineapple

위의 예시에서 분할 기준에 대해 조금 더 자세히 설명하자면, 문자열 "apple"이 포함된 행을 찾아서 그 이전 행까지를 복사하여 저장하게 된다. 위의 경우 "apple" 문자열이 포함된 행을 경계로 했는데 첫번째 행에 apple이 있었기 때문에 맨 처음 분할결과는 크기가 0이다. 이런 파일을 제외하기 위해 -z 옵션을 추가하자.

# 문자열 "apple"이 포함된 행을 기준으로 반복 분할, 크기 0인 결과는 제외
csplit -z -f "output" sample.txt '/apple/' '{*}'

cat output00
1 apple
2 orange
...
cat output03
8 pineapple

경계가 되는 행을 제외하고 결과를 생성할 수도 있다. --suppress-matched 옵션을 추가하면 된다. 위 예시의 경우에는 "apple"이 포함된 행이 결과에서 제외될 것이다.

# 문자열 "apple"이 포함된 행을 기준으로 반복 분할, 해당 행은 출력에서 제외
csplit --suppress-matched -z -f "output" sample.txt '/apple/' '{*}'

cat output00
2 orange

cat output01
4 banana
5 cherry

cat ouput02
7 orange

사용법이 약간 복잡하긴 하나, 파일 분할에 꽤 요긴하다. 더 자세한 사용법은 man 페이지를 참조하자.

# man 페이지 표시
man csplit

728x90
Posted by 반달가면