regsub — 정규식 패턴 매칭 기반 치환

regsub — 정규식 패턴 매칭 기반 치환

문자열에서 특정 패턴에 맞는 부분을 찾아 다른 문자열로 바꾸고 싶을 때가 많아요. regsub는 정규식으로 문자열과 일치시키고, 그 일치 부분을 지정한 치환 문자열로 교체해 주는 명령이에요. 매치 변수 대신 결과를 변수에 저장하거나 반환받는 차이만 빼면 regexp와 비슷한 구조예요.

출처: 문서

본문

문법

regsub ?switches? exp string subSpec ?varName?

동작 방식

이 명령은 정규식 expstring과 일치시키고, varName이 주어져 있으면 그 이름의 변수로 string을 복사하거나, varName이 없으면 string을 반환해요.

매치가 있다면 stringvarName(또는 varName이 없을 때 이 명령의 결과)으로 복사하면서, exp와 일치한 string 부분을 subSpec으로 교체해요.

subSpec& 또는 \0을 포함하면, 치환에서 그 부분이 exp와 일치한 string 부분으로 교체돼요.

subSpec\n(여기서 n은 1부터 9 사이의 숫자)을 포함하면, 치환에서 그 부분이 exp의 n번째 괄호 부표현식과 일치한 string 부분으로 교체돼요.

subSpec에서 추가 백슬래시를 사용해 &, \0, \n, 그리고 백슬래시 자체의 특별한 해석을 막을 수 있어요. subSpec에서 백슬래시를 쓰면 Tcl 파서의 백슬래시 사용과 충돌하는 경향이 있으므로, 백슬래시를 포함한다면 subSpec을 중괄호로 감싸는 게 일반적으로 가장 안전해요.

처음 인자가 -로 시작하면 스위치로 취급돼요. 지원되는 스위치는 다음과 같아요.

스위치

  • -allstring에서 exp와 일치하는 모든 범위를 찾아 각 범위에 대해 치환을 수행해요. 이 스위치가 없으면 첫 번째 일치 범위만 찾아 치환해요. -all이 지정되면 &\n 시퀀스는 각 치환마다 해당 매치의 정보를 사용해 처리돼요.
  • -expanded — 공백과 주석이 무시되는 확장 정규식 문법을 사용하게 해요. (?x) 옵션과 같아요.
  • -line — 줄바꿈 민감 매칭을 활성화해요. [^ 대괄호 표현식과 .는 줄바꿈과 일치하지 않고, ^는 줄바꿈 뒤의 빈 문자열과, $는 줄바꿈 앞의 빈 문자열과 일치해요. (?n) 옵션과 같아요.
  • -linestop[^ 대괄호 표현식과 .가 줄바꿈에서 멈추게 해요. (?p) 옵션과 같아요.
  • -lineanchor^$가 각각 줄의 시작과 끝과 일치하게 해요. (?w) 옵션과 같아요.
  • -nocasestring의 대문자를 exp와 매칭하기 전에 소문자로 변환해요. 다만 subSpec이 지정한 치환은 변환 전 원래 형태의 string을 사용해요.
  • -start index — 매칭을 시작할 string 안의 문자 인덱스 오프셋을 지정해요. string index의 인덱스 인자와 같은 방식으로 해석돼요. 이 스위치를 쓸 때 ^는 줄의 시작과 일치하지 않고, \\A는 여전히 index에서의 문자열 시작과 일치해요. index는 입력 문자열의 범위로 제한돼요.
  • -- — 스위치의 끝을 표시해요. 다음 인자는 -로 시작하더라도 exp로 취급돼요.

varName이 주어지면 이 명령은 찾아서 치환한 일치 범위의 개수를 반환하고, 그렇지 않으면 치환 후의 문자열을 반환해요. 정규식 해석에 대한 자세한 내용은 regexp 매뉴얼 항목을 참고하세요.

예제

변수 string 안에서 단어 단위로 존재하는 모든 foo 인스턴스를 bar로 바꾸기:

regsub -all {\mfoo\M} $string bar string

("기본 정규식" 문법을 쓰면):

regsub -all {(?b)\<foo\>} $string bar string

단어 interesting의 첫 인스턴스(대문자화 여부와 무관)에 큰따옴표 삽입하기:

regsub -nocase {\yinteresting\y} $string {"&"} string

regsubsubst를 조합해 모든 비-ASCII 및 Tcl 특수 문자를 \u 이스케이프 시퀀스로 변환하기:

# 이 RE는 거의 모든 "나쁜" 문자에 대한 문자 클래스일 뿐
set RE {[][{};#\\\$ \r\t\u0080-\uffff]}
# 대괄호 안의 Tcl 스크립트 조각으로 치환할 것
set substitution {[format \\\\u%04x [scan "\\&" %c]]}
# 이제 치환을 적용해 변환의 계산 부분을 수행할 subst-문자열을 얻는다.
# 백슬래시-개행은 특별 시퀀스이므로 개행은 string map으로 특별 처리한다는 점에 주의
set quoted [subst [string map {\n {\\u000a}} \
    [regsub -all $RE $string $substitution]]]

더 알아보기

  • regexp: 정규식 매칭
  • re_syntax: 정규식 문법 전체
  • subst, string: 치환과 문자열 처리