지금까지 우리는 원하는 걸 찾는 방법을 익혀왔어요. 그런데 정규식의 진짜 힘은 찾은 걸 바꾸는 데서 터져요. 전화번호에서 하이픈만 쏙 빼거나, 지저분하게 붙은 공백을 정리하거나, 웹에서 긁어온 글의 태그를 몽땅 벗겨내는 일을요. 이렇게 찾아서 다른 글자로 갈아 끼우는 걸 치환(바꾸기)이라고 해요. 손으로 하면 반나절 걸릴 정리 작업을 정규식 치환 한 줄로 끝낼 수 있어요. 이번 편만 따라오면 여러분도 지저분한 텍스트를 순식간에 정돈할 수 있게 돼요. 파이썬으로 하나하나 직접 쳐보면서 익혀볼게요.

17.1 치환이 뭔가요?

치환은 말 그대로 찾은 부분을 다른 문자열로 갈아 끼우는 일이에요. 파이썬에서는 re.sub라는 함수를 써요. sub는 substitute(대체하다)의 앞글자예요. 쓰는 모양은 이래요.


re.sub(패턴, 바꿀문자열, 대상)


첫 번째 자리에 찾을 패턴, 두 번째 자리에 바꿔 넣을 문자열, 세 번째 자리에 대상 텍스트를 넣어요. 그러면 대상에서 패턴에 맞는 부분을 전부 찾아 두 번째 문자열로 바꾼 새 문자열을 돌려줘요. 원본은 그대로 두고 바뀐 결과를 새로 만들어 준다는 점만 기억해 두세요.


혹시 파이썬의 문자열 replace 메서드를 써본 적 있으신가요? replace정확히 그 글자만 바꿀 수 있어요. 반면 re.sub패턴에 맞는 것을 바꿔요. 그래서 전화번호처럼 생긴 것, 날짜처럼 생긴 것을 한꺼번에 갈아 끼울 수 있는 거예요. 이 차이가 바로 정규식 치환의 힘이에요. 그리고 하나 더, re.sub는 기본적으로 대상 안에서 맞는 부분을 전부 바꿔줘요. 하나만 바꾸고 멈추는 게 아니라 처음부터 끝까지 훑으면서 다 처리한다는 거죠. 이제 상황별로 하나씩 해볼게요.

17.2 특정 글자를 지우고 싶어요

바꿀 문자열 자리에 빈 문자열(아무것도 없음, '')을 넣으면 어떻게 될까요? 찾은 걸 아무것도 아닌 것으로 바꾸니까 결국 삭제가 돼요. 전화번호에서 하이픈을 없애볼게요.


import re


re.sub(r'-', '', '010-1234-5678')


결과는 '01012345678'이에요. 하이픈 두 개가 한 번에 싹 사라졌죠? 앞에서 re.sub가 맞는 걸 전부 바꾼다고 했으니, 하이픈이 두 개든 세 개든 한 방에 다 지워지는 거예요. 이렇게 빈 문자열로 치환하면 지우기가 된다는 걸 꼭 기억해 두세요. 특정 기호나 글자를 걷어낼 때 정말 자주 써먹어요. 예를 들어 금액에서 콤마를 빼거나, 문장에서 특수 기호를 걷어낼 때도 똑같은 방식이에요.

17.3 여러 공백을 한 칸으로 정리하고 싶어요

복사해서 붙여넣은 글을 보면 공백이 두세 칸씩 붙어 있을 때가 많아요. 이걸 한 칸으로 정리해볼게요. 공백류(스페이스, 탭 같은 빈 칸)를 뜻하는 \s에 한 개 이상을 뜻하는 +를 붙여 \s+로 공백 덩어리를 통째로 잡고, 한 칸짜리 공백으로 바꾸는 거예요.


re.sub(r'\s+', ' ', 'a b c')


결과는 'a b c'예요. 세 칸, 다섯 칸이던 공백이 전부 한 칸으로 정리됐어요. 이건 텍스트를 깔끔하게 다듬는 정규화(형식을 하나로 통일하기) 작업의 단골 손님이에요. 사용자가 아무렇게나 띄어 쓴 입력을 정돈할 때 특히 유용해요.

17.4 HTML 태그를 벗겨내고 싶어요

웹에서 긁어온 글에는 <b><i> 같은 태그가 섞여 있어요. 본문 글자만 남기고 태그를 다 지우고 싶을 때가 있죠. 이때 패턴은 <[^>]+>예요. 조금 복잡해 보이지만 뜯어보면 쉬워요. <로 시작해서, [^>]+로 닫는 꺾쇠 >가 아닌 글자를 한 개 이상 먹고, >로 끝나는 거예요. 즉 꺾쇠로 감싼 덩어리 하나를 뜻해요.


re.sub(r'<[^>]+>', '', '<b>Hello</b> <i>World</i>')


결과는 'Hello World'예요. 태그만 쏙 빠지고 글자만 남았죠? 여기서 .* 대신 [^>]+(닫는 꺾쇠가 아닌 글자, 부정 문자 클래스)를 쓴 게 중요한 요령이에요. .*는 욕심을 부려서 여러 태그를 통째로 삼켜버리는데, [^>]+는 닫는 꺾쇠 전까지만 딱 잡아서 태그를 하나씩 정확히 지워줘요. 이 요령은 태그뿐 아니라 대괄호 안 내용, 따옴표 안 내용처럼 여는 기호와 닫는 기호가 짝을 이루는 것을 다룰 때 두루 통해요.


한 가지만 덧붙일게요. 이렇게 태그를 벗겨내는 건 간단한 정리 작업엔 충분하지만, 구조가 복잡하게 얽힌 진짜 HTML 문서를 다룰 땐 정규식보다 전용 파서(HTML을 제대로 해석하는 도구)를 쓰는 게 안전해요. 정규식은 어디까지나 가벼운 정리용이라고 생각해 두시면 좋아요.

17.5 조각을 나눠 순서를 바꾸고 싶어요

치환의 진짜 묘미는 여기 있어요. 찾은 걸 그냥 지우는 게 아니라, 조각으로 나눈 뒤 순서를 바꿔 다시 조립할 수 있거든요. 괄호로 묶어 저장하는 캡처 그룹을 쓰면 돼요. 날짜 2024-01-1515/01/2024 형식으로 뒤집어볼게요.


먼저 패턴 (\d{4})-(\d{2})-(\d{2})로 연도, 월, 일을 각각 괄호로 묶어 잡아요. 괄호 하나가 조각 하나예요. 이러면 왼쪽 여는 괄호가 나온 순서대로 차례로 1번, 2번, 3번 그룹이 돼요. 그러니까 (\d{4})가 1번(연도), (\d{2})가 2번(월), 마지막 (\d{2})가 3번(일)이에요. 바꿀 문자열에서는 \1, \2, \3으로 그 조각들을 번호로 불러올 수 있어요.


re.sub(r'(\d{4})-(\d{2})-(\d{2})', r'\3/\2/\1', '2024-01-15')


결과는 '15/01/2024'예요. \3(일), \2(월), \1(연도) 순서로 다시 조립했더니 날짜 형식이 뒤집혔죠? 이렇게 번호로 조각을 재배치하는 건 날짜나 이름 형식을 바꿀 때 아주 요긴해요. 값을 지우거나 더하지 않고 순서만 바꾸니 안전하고요.

17.6 언어마다 표기가 조금 달라요

참고로 바꿀 문자열에서 그룹을 부르는 표기는 언어마다 조금 달라요. 파이썬은 \1, \2처럼 역슬래시를 쓰고, 자바스크립트는 $1, $2처럼 달러 기호를 써요. 뜻은 똑같이 1번, 2번 그룹이 잡은 내용이에요. 그리고 파이썬에서 패턴이나 바꿀 문자열 앞에 붙은 r원시 문자열(역슬래시를 특수 처리 없이 그대로 취급) 표시라, 역슬래시가 많은 정규식에서는 습관처럼 붙여 주면 편해요.

17.7 정리

오늘 배운 걸 정리해볼게요. 치환은 re.sub(패턴, 바꿀문자열, 대상) 형태로 쓰고, 찾은 부분을 다른 글자로 갈아 끼워요. 바꿀 문자열을 빈 문자열로 두면 삭제가 되고요. \s+로 공백을 한 칸으로 정리하고, <[^>]+>로 태그를 벗겨냈어요. 무엇보다 캡처 그룹\1, \2 표기를 조합하면 조각을 원하는 순서로 재배치할 수 있다는 게 핵심이에요. 찾기에서 한 걸음 더 나아가 바꾸기까지 손에 익으면, 지저분한 텍스트를 다루는 일이 한결 수월해질 거예요. 직접 값을 바꿔가며 몇 번만 쳐보면 금방 손에 붙어요.