본문 바로가기

흔한말 (collection)/Python

정규표현식 잘 몰라도 코드 짤 수 있어요

300x250

어.........음...

다만 코드가 엄청나게 길고 복잡해 질 뿐이죠.
네.. 이 말은 정규표현식에 대해 알아야 한다는 말입니다.

그런데 오히려 알아야한다는 말만 많이 듣고,
한두번씩 배움을 미루다 보면 거북하고 거추장스러워서 점점 배우기 싫어집니다.
거추장스러움을 없애기 위한 방법인데 말이죠.

/[^a-zA-Z0-9가-힣ㄱ-ㅎ]/g


정규식이라고 해서 검색했는데, 이런 예제를 보고 나면,
암호문을 본 듯한 기분에 일단 쉬고 싶어집니다.
그래서 오늘은 많은 내용들을 손질해서, 먹을 부분만 딱 남겨 보여 드리겠습니다.

regex 언제 쓰나?

흔히 regex라고 줄여쓰는 regular expression (정규표현식) 은,
데이터로 들어온 문자열을 판별할때 쓰는데, 우리는 살면서 많은 글자들을 바탕으로 움직입니다.

길가의 간판에 써진 글씨들...
새로 나온 노래의 제목...
마트에서 산 휴지에 써있는 제품명...
주민등록번호...
은행계좌번호...
전자제품의 일련번호...
나의 이메일 주소...

등등의 수 많은 글씨와 숫자, 기호에 둘러싸여 있습니다.
우리의 생활이 글자로 되어있으니,
프로그래밍에서도 당연히 이런 문자열들을 가지고 이런저런 처리들을 하게 됩니다.

어떤 사이트에 회원가입을 할 때를 떠올려볼까요.
주민등록번호를 입력하는 칸에 문자를 입력하면,
아예 작성되지 않거나 오류가 있다는 메세지를 띄워주는 사이트들이 대부분입니다.

어떻게 이런 것을 할 수있을까요?

find()와는 다르다. find()와는...

언뜻 생각해보면, 파이썬 기초문법을 배울때, 문자열을 검사할 수 있는 몇 가지 함수들을 배웁니다.
바로 find() 같은 함수가 그렇죠?
‘원 문자열’.find(’검색대상 문자열’)
의 형태로 코드를 작성하게 되면 원 문자열에서 검색대상 문자열이 몇번째 인덱스에 위치하는 지를 알려주는 함수입니다.

그 밖에도
’검색대상 문자열’ in ‘원 문자열’ 이라고 코드를 작성하면,
그 자체로 포함여부를 True, False 로 반환해 주기도 합니다.
그럼 이 코드들을 적절히 사용하면 특정 문자열이 내가 원하는 범주에 속하는 문자열인지
얼마든지 판단하는 코드를 짤 수 있지 않을까요?

네 당연히 가능하지만.
엄청나게 복잡한 코드가 될 것입니다.
단지 문자열을 처리하는 부분만 몇십줄이 넘어가는 코드가 될 수도 있죠.

“\d” 그리고 “[A-Z]” 만 알면 나머지는 알아서 배울 수 있다.

딱, 두가지만 알고 가면 됩니다.

"\d" 는 모든 숫자

"[A-Z]" 는 모든 알파벳
(대문자일 경우. 소문자를 보고 싶은 경우엔 [a-z]로 명기.)


을 나타내는 정규표현식입니다.
이해가 완벽하지 않아도 일단 저걸 머리속에 박아두시면,
그 다음 예제를 보고 이해할 수 있습니다.

일단 이것부터 해보자

예를 들어서 봅시다.

예시 코드에 보면, mystring이라는 변수에 리스트 하나가 들어가있죠?

문자열 4개가 들어가 있는 리스트인데, 어떤 컴퓨터주변기기 제조사의 제품들 모델 번호를 나열한 리스트입니다.
주석에 보이는 것 처럼 각각 순서대로 마우스, 키보드1, 키보드2, 키보드3 의 순서로 리스트가 만들어져있네요.
이 여러가지 모델 명 중에 키보드에 해당하는 것만 추출하려면? 어떻게 해야 할 까요?

일단 정규표현식을 처리하는 모듈을 하나 가져옵니다.

이렇게 맨 위에 적어두고요.

그다음엔 마우스 중에서 KY로 시작하는 것들만 추려보도록 하겠습니다.

위 그림처럼 코드를 작성했습니다.

이 코드를 살펴보면,

  1. 조사하고자 하는 문자열의 앞의 2자리가 대문자 알파벳이고,
  2. 언더바가 등장하기 전까지 4개의 숫자가 등장하며,
  3. 언더바 뒤로는 다시 6개의 숫자가 이어지고,
  4. 마지막으로는 소문자 알파벳 하나가 이어진다.

라는 조건을 만족하는지를 검사한 다음. ( re.search( )메소드로 검사합니다. )

맞으면 참, 틀리면 거짓 을 결과로 반환하도록 되어있습니다.
실행결과를 볼까요?

조건에 해당하는 인덱스2와 3의 항목에만 참이 붙어나온것을 확인할 수 있죠?
이번에는 모든 키보드를 함께 검색해보고 싶습니다. 그럴땐 어떻게 할까요?

인덱스1의 키보드는: 언더바 뒤의 숫자가 7자리이고,
인덱스2,3의 키보드는: 언더바 뒤의 숫자가 6자리 입니다.

그럴 때는 숫자가 몇번 반복되는지를 숫자 표현식 뒤에 { }로 표시해 주면 됩니다.
\d{6, 7}의 의미는
“숫자가 6번 혹은 7번 반복되고, 그다음 소문자 알파벳이 나온다.”
라는 의미로 해석하시면 됩니다.

익숙해지면 이것도 해보길

그러고 보니 기존의 코드는 숫자가 4번 나오면 바보같이 “\d\d\d\d”라고 써 놓았죠?
이를 줄여서 축약형으로 코드를 다시 정리해봅시다.

정규표현식 부분이 상당히 짧게 처리된것을 확인할 수 있네요!


......
오늘 다룬 내용은 정규표현식의 문법 중 극히 일부만을 대상으로 한 예제입니다만,
모든 숫자와 모든 영문자를 정규표현식으로 표현할 수 만 있으면,
더듬 더듬 짚어가며 어떻게든 문자열을 판별해 낼 수 있습니다.

오늘 배운 제한된 문법으로 원하는 코드를 구현해보다가,
구현할 수 없거나 불편한 점을 느낀다면
그 때, 비로소 구글에 regex라고 검색해서 나오는 수 만 가지 검색결과들을
흡수해서 사용할 수 있게 되실거에요.


p.s. 저는 파이썬 예제를 VScode나 주피터노트북이 아닌, "Dynamo Sandbox" 프로그램을 이용해 작성하고 있습니다.
쉽고 유용한 비주얼 프로그래밍 툴인 "Dynamo"를 통해 파이썬 예제를 직접 작성해보고 싶은 분들은 하기 링크를 참조하시면 됩니다.
https://hnanmal.tistory.com/4

Dynamo Sandbox 최신버전 다운받기

레빗과 연결되어 동작하는 다이나모도 강력하지만, 다이나모 샌드박스는 잘 사용하면 레빗없이도 형상과 관련된 각종 알고리즘을 테스트하고 만들어내는 훌륭한 도구가 될 수 있습니다. 또한

hnanmal.tistory.com

반응형