Saturday, April 15, 2006
Perl/펄] 텍스트 파일에 행번호 붙여, 화면에 출력 또는 파일로 저장
텍스트 파일(text file)에 행번호(line numbers) 붙이기
프로그래밍 강좌를 할 때, 소스에 행번호를 붙여 설명한다든지 할 때 유용.
#!/usr/bin/perl
use strict; use warnings;
my $line = 1;
while (<>) {
printf("%4d: %s", $line, $_);
$line++;
}
use strict; use warnings;
my $line = 1;
while (<>) {
printf("%4d: %s", $line, $_);
$line++;
}
이렇게 짧은 코드로 행번호 붙이기를 훌륭하게 해낼 수 있다. C나 자바 같은 다른 언어들이 산문이라면, 펄은 흔히 시(詩)에 비유되는데, 펄이 얼마나 함축적이고 강력한 언어인지 실감할 수 있는 예제이다. (참고로, printf 함수는 C에도 있고 펄에도 있음)
만약 C언어로 행번호 붙이기 프로그램을 만들었다면 2~3페이지 분량은 족히 되었을 것이다. include 를 하고, 옵션을 분석하고 파일을 열고 닫고 하느라 무척 귀찮았을 것이다.
<> 이것이 바로 펄의 전매특허인 "다이아몬드 연산자 (diamond operator)"이다. 이것으로 파일(명령행에서 옵션으로 지정해 준 파일)을 자동으로 열고 닫고 할 수 있으며, 또한 STDIN 입력도 받을 수 있다(그래서 이 프로그램에 대상 파일을 지정해 주지 않고 실행시키면 입력 대기 상태가 되어 화면에 아무것도 나오지 않는다. 이때는 Ctrl+Z를 눌러 빠져 나와야 한다. 유닉스/리눅스에서는 Ctrl-D). <> 이렇게 단 2글자로 말이다.
$_ 역시 펄의 전매특허인 "디폴트 변수(default variable)"다. 뻔한 변수는 굳이 선언하고 이름을 정해줄 필요 없이 간단히 이것을 쓰면 된다. 위의 소스에서, $_ 에는 <>로 연 텍스트 파일의, 각 행이 현재 들어가 있다.
다만 "다이아몬드 연산자"로 이진 파일은 처리할 수 없고(해본 적이 있는데 되지 않았음), 몇 가지 제한이 있다. (한 프로그램에 2개의 다이아몬드 연산자를 쓸 수 없는 등의 제한) 텍스트 파일만을 간단히 처리할 때 사용하는 연산자이다. 그래서 복잡한 작업을 할 때는 C언어처럼 open 으로 파일을 열어야 한다.
본론으로 들어가서, 행번호 등의 문자열 조작은, 펄로 간단히 만들어서 쓰는 것이 융통성이 있다. 다음과 같이 각자의 입맛에 맞게 마음대로 포맷을 변경할 수 있기 때문이다.
행 번호를 16진수로 출력:
#!/usr/bin/perl
use strict; use warnings;
my $line = 1;
while (<>) {
printf("%04X: %s", $line, $_);
$line++;
}
use strict; use warnings;
my $line = 1;
while (<>) {
printf("%04X: %s", $line, $_);
$line++;
}
행번호 붙여 인쇄
인쇄를 하기 위해서는 위의 펄 프로그램의 화면 출력 결과를 텍스트 파일로 만든 후, 그것을 울트라에디트(UltraEdit)나 메모장(Notepad) 등의 텍스트 에디터에서 불러서 인쇄하면 된다.
명령 프롬프트에서, 화면 출력을 파일로 만들 때에는 다음과 같이 > 기호를 사용해 '재지향'하면 된다. 예를 들어, 위의 소스를 foo.pl 이라는 이름으로 저장하고, 행번호를 붙일 텍스트를 in.txt 라고 이름 붙였을 경우:
foo.pl in.txt > out.txt
기타
유니코드(UTF-8)의 경우:
이 펄 스크립트는 유니코드(UTF-8) 텍스트 파일도 입출력되지만, 화면으로 바로 출력하면, 명령 프롬프트 창에서 한글 글자들이 깨져 보인다. 재지향을 사용해 결과를 파일로 바로 저장하는 것이 좋다.
위의 펄 소스를 0.pl 이라는 이름으로 저장하고, 행번호를 붙일 파일을 0.txt 라는 이름으로 저장한 후, 명령 프롬프트에서 실행시켰을 경우, 다음과 같이 각 줄에 번호가 붙은 채 출력(파일 이름은 상관 없음):
D:\Z>0.pl 0.txt
1:
2: 청포도
3:
4:
5: 이육사
6:
7:
8: 내 고장 칠월은
9: 청포도가 익어 가는 시절
10:
11: 이 마을 전설이 주저리주저리 열리고
12: 먼 데 하늘이 꿈꾸며 알알이 들여와 박혀
13:
14: 하늘 밑 푸른 바다가 가슴을 열고
15: 흰 돛단배가 곱게 밀려서 오면,
16:
17: 내가 바라는 손님은 고달픈 몸으로
18: 靑袍를 입고 찾아온다고 했으니
19:
20: 내 그를 맞아, 이 포도를 따먹으면
21: 두 손은 함뿍 적셔도 좋으련
22:
23: 아이야, 우리 식탁엔 은쟁반에
24: 하이얀 모시 수건을 마련해 두렴
25:
D:\Z>
이것은 행번호를 16진수로 출력했을 경우:
D:\Z>0.pl 0.txt
0001:
0002: 청포도
0003:
0004:
0005: 이육사
0006:
0007:
0008: 내 고장 칠월은
0009: 청포도가 익어 가는 시절
000A:
000B: 이 마을 전설이 주저리주저리 열리고
000C: 먼 데 하늘이 꿈꾸며 알알이 들여와 박혀
000D:
000E: 하늘 밑 푸른 바다가 가슴을 열고
000F: 흰 돛단배가 곱게 밀려서 오면,
0010:
0011: 내가 바라는 손님은 고달픈 몸으로
0012: 靑袍를 입고 찾아온다고 했으니
0013:
0014: 내 그를 맞아, 이 포도를 따먹으면
0015: 두 손은 함뿍 적셔도 좋으련
0016:
0017: 아이야, 우리 식탁엔 은쟁반에
0018: 하이얀 모시 수건을 마련해 두렴
0019:
D:\Z>
0001:
0002: 청포도
0003:
0004:
0005: 이육사
0006:
0007:
0008: 내 고장 칠월은
0009: 청포도가 익어 가는 시절
000A:
000B: 이 마을 전설이 주저리주저리 열리고
000C: 먼 데 하늘이 꿈꾸며 알알이 들여와 박혀
000D:
000E: 하늘 밑 푸른 바다가 가슴을 열고
000F: 흰 돛단배가 곱게 밀려서 오면,
0010:
0011: 내가 바라는 손님은 고달픈 몸으로
0012: 靑袍를 입고 찾아온다고 했으니
0013:
0014: 내 그를 맞아, 이 포도를 따먹으면
0015: 두 손은 함뿍 적셔도 좋으련
0016:
0017: 아이야, 우리 식탁엔 은쟁반에
0018: 하이얀 모시 수건을 마련해 두렴
0019:
D:\Z>
관련 포스트:
[Perl/펄] 윈도우용 펄(ActivePerl) 설치법
[QnA] 울트라에디트에서 행번호를 붙여서 출력/인쇄할 수 있나요?
tag: perl
Perl | 펄
<< Home