프날 오토핫키 강좌  v2

⚠ 이 강좌는 오토핫키 v2를 다룹니다

지금 보시는 강좌는 과거 오랜 시간동안 알려진 오토핫키(v1.1)의 차세대 버전인 오토핫키 v2를 다루고 있습니다.
만약 구버전인 '오토핫키 v1.1'의 강좌를 찾으신다면 프날 오토핫키 강좌(https://pnal.kr)를 봐주시면 되지만, 새로 오토핫키를 배우신다면 v2 버전을 배우시는 것을 강력히 추천드립니다.

85. Loop Parse


뜬금없이 Loop를 다시 배우는가 싶으시겠지만, 이번엔 문자열 가공에 필요한 필수 테크닉 중 하나인 Loop Parse 구문을 배워보고자 합니다. 이번 강만 끝내면 '문자열 처리 기본편'의 개념은 모두 마친 것이니 조금만 더 힘내보자고요.

지금까지 아주 긴 문자열을 특정 구분자를 기준으로 작업하기 위해 StrSplit을 사용한 후 Loop를 이용하여 배열을 탐색하는 과정을 거쳤습니다. 그러나 이 방법은 배열 공간만큼의 메모리를 소모하며 문자열의 일부만 작업할 때에도 전체 문자열을 구분자로 쪼개는 작업이 선행되어야 하는, 약간 비효율적인 방법입니다.

이번에 배울 Loop Parse 구문을 이용하면 배열을 쓰지 않고도 전체 문자열을 구분자를 기준으로 작업할 수 있습니다. 예를 들어서 '-'를 구분자로 사용하여 Loop Parse를 사용하면 전체 문자열을 '-'을 기준으로 하나씩 쪼개며 읽어올 수 있습니다. 오늘은 이토록 유용한 Loop Parse 구문을 배워보겠습니다.

파싱

앞으로 강의에서 '파싱(Parsing)'이라는 용어를 많이 사용할 것입니다. 영어를 어느정도 배우신 분들은 눈치 채셨겠지만, 파싱(Parsing)은 그 동사 원형인 Parse에 '~하는 것'이라는 -ing가 연결된 형태의 단어입니다. 그렇다면 Parse는 무엇일까요?

Parse는 그 자체로 '문장의 구문을 분석하다'라는 뜻을 갖고 있습니다. 따라서 Parsing은 '구문 분석'이라는 뜻이 됩니다. 컴퓨터 분야에서 '파싱'이라고 하면 '전체 문자열을 이용해서 요목조목 분해하거나 분석하는 것'을 의미하고, 더 나아가 '전체 문자열을 가공하여 필요한 일부 문자열을 가져오는 행위'를 말하기도 합니다.

지금까지 배워온 문자열 처리 함수로 텍스트를 가공하는 모든 행동이 '파싱'인 것입니다.

Loop Parse

Loop Parse는 전체 문자열을 특정 구분자로 나누어서, 한 번에 하나씩 부분 문자열을 가져오는 제어문입니다. 쉽게 말하면 전체 문자열을 구분자로 끊어서 읽어주는 역할을 합니다.

Loop Parse String [, DelimiterChars, OmitChars]
Loop Parse의 원형

반복문은 함수가 아니기 때문에 LoopParse 사이에 괄호를 열지 않습니다. 기본 반복문을 배울 때 이미 언급한 내용이죠?

  • String: 전체 문자열입니다.
  • DelimiterChars: 구분자입니다.
  • OmitChars: 양 끝에서 제외할 문자입니다. 여러 문자를 지정 가능합니다.

이 또한 반복문이기 때문에, 아래와 같이 블록을 열어주어야 합니다.

1Loop Parse String, DelimiterChars
2{
3    ...//여기서 부분 문자열을 1회 반복마다 하나씩 가져온다.
4}

반복문 내부에선 구분자에 의해 쪼개진 문자열을 반복시마다 사용할 수 있습니다. 첫 번째 반복에선 첫 부분을, 두 번째 반복에선 두 번째 부분을 이용할 수 있습니다. 예를 들어서 아래와 같은 문자열이 있다고 해봅시다.

낙엽은 가을 바람을 원망하지 않는다.

이 문장에서 구분자를 공백(띄어쓰기)으로 하여 Loop Parse를 사용하면, 그 안에서 첫 번째 반복엔 낙엽은, 두 번째 반복에선 가을, 세 번째 반복에선 바람을을 이용할 수 있습니다. 원망하지, 않는다.까지 총 5번 반복되겠네요.

A_LoopField

A_LoopFieldLoop Parse 블록 안에서 쓰이는, 현재 반복에서의 부분 문자열이 담긴 내장 변수입니다.

위의 예시를 다시 가져와보면, 첫 번째 반복에선 A_LoopField의 값이 낙엽은일 것입니다. 두 번째 반복부터 다섯 번째 반복까지 이 변수의 값은 가을, 바람을, 원망하지, 않는다.로 변할 것입니다. 반복문만으로 문장 전체를 구분자를 기준으로 끊어서 읽을 수 있는 것이죠.

예제

아마 여러분 중 대부분은 이해하지 못하셨을 수도 있겠습니다. 제가 설명을 잘 못하기도 했고요, 사실 쉽게 납득되는 개념도 아니고요. 그래서 아래 예제를 통해 실 사용례를 익혀보겠습니다.

1. 콤마를 기준으로 반복하며 모든 수 더하기

1numbers := "100, 53, 80, 75, 90"
2sum := 0
3Loop Parse numbers, ","
4{
5    sum += A_LoopField
6}
7MsgBox(sum)
예제 1. 콤마로 구분된 수의 합 구하기

전체 문자열을 콤마를 기준으로 반복하면 각 반복마다 수만 담길 것입니다. 여기선 각 반복마다 100, 53, 80, 75, 90A_LoopField 변수에 담깁니다. 오토핫키는 수가 필요한 부분에서는 문자열도 가능한 한 수로 변환하려고 하기 때문에, 각 수 앞에 한 칸씩 있는 공백은 신경 쓸 필요가 없습니다. 그 공백은 += 연산을 할 때 자동으로 제거됩니다.

Loop Parse도 반복문이기 때문에 그 블록 안의 내용이 한 줄일 땐 중괄호를 생략할 수 있습니다. 따라서 4번 줄과 6번 줄은 적지 않아도 무방합니다.

1. 개행을 기준으로 반복하며 모든 수 더하기

1numbers := "100`n53`n80`n75`n90"
2sum := 0
3Loop Parse numbers, "`n", "`r"
4{
5    sum += A_LoopField
6}
7MsgBox(sum)
예제 2. 개행으로 구분된 수의 합 구하기

예제 1과 거의 동일합니다. 다만 앞선 강의에서 언급하였듯, 개행을 기준으로 문자열을 쪼갤 땐 `r을 OmitChars에 지정해주어야 한다는 것을 꼭 유의해야합니다. (3번 줄)

이 예제는 명백하게 `n로 개행된 문자열을 가지고 파싱하니 `r을 OmitChars에 적지 않아도 무방하지만, 실무에서는 텍스트 파일의 내용이 입력되는 경우가 많기 때문에 반드시! 개행을 기준으로 쪼갤 땐 OmitChars에 `r을 적는다!는 사실을 기억해야 합니다.

Tip: Loop Parse도 반복문입니다!

Loop Parse 구문도 반복문이기 때문에, 반복문 내에서 사용할 수 있는 BreakContinue와 같은 지시문을 모두 쓸 수 있으며, A_Index 내장 변수 또한 쓸 수 있습니다.

질문하러 가기