. 분석 예

분석기 코드는 이미 다 작성했지만 코드만 보고서 동작방식을 한눈에 이해하기는 어려울 것 같다. 그래서 분석기가 실제 문장을 어떤 식으로 분석하는지 코드의 실행 과정을 따라 가면서 같이 분석을 해보도록 하자. 다음 문장은 세 개의 유닛으로 구성된 비교적 간단한 문장이다.

 

int var; // comment

 

이 줄은 문서의 첫 줄이므로 ParseLine 함수는 최초 노말 컨텍스트에서 분석을 시작하며 첫 번째 유닛에 노말 스타일을 기록할 것이다. 시작 스타일을 기록한 후 첫 문자부터 끝 문자까지 루프를 돌며 문서를 분석한다. 이 상태에서 오프셋 3의 공백을 만날 때까지 /*, //, ", 중 어느 것도 찾지 못하므로 계속 루프를 돌기만 한다. 오프셋 3에서 공백 즉 구분자를 만나면 여기까지 읽은 문자열이 키워드나 숫자 또는 전처리기인지 점검한다. 이때 점검 대상 문자열은 앞쪽 세 글자이다. 공백이라는 구분자를 만났기 때문에 idend i-1이 된다.

이 세 글자 int IsKeyword 함수에 의해 키워드로 조사되므로 다음 유닛에 키워드 스타일과 노말 스타일을 기록한다. 최초 기록되어 있던 노말 스타일은 길이가 0이므로 삭제되고 다음 두 개의 스타일이 기록된다.

키워드를 조사한 후 idpos는 구분자 다음 위치인 오프셋 4로 이동하게 되며 루프의 선두로 돌아가 분석을 계속한다. var; 문자열은 키워드도 숫자도 아니므로 특별한 처리를 하지 않으며 //를 만나면 한 줄 주석 상태로 컨텍스트가 변경된다. 여기까지 발견된 문자열 var;은 키워드, 숫자, 전처리기 중 어떤 것에도 해당되지 않으므로 문자열 검색은 실패할 것이다. 한 줄 주석 스타일이 기록되고 한 줄 주석 이후는 더 분석할 필요가 없으므로 EndParse로 점프하여 컨텍스트를 기록한 후 분석을 마친다. 분석결과는 다음과 같다.

세 개의 유닛이 작성되었으며 컨텍스트는 한 줄 주석값인 2가 되어 있다. ApiEdit pInfo에 작성된 분석결과를 보고 스타일의 색상대로 문서를 출력한다. GetStyleColor 함수는 5번 스타일을 빨간색으로 정의하고 있으므로 0~2오프셋까지의 int는 빨간색으로 출력된다. 오프셋 3이후는 ApiEdit의 기본색으로 출력되다가 오프셋 9 이후는 다시 1번 스타일(주석)의 색상인 회색 바탕에 검정색으로 출력될 것이다. 출력 결과는 다음과 같다.

다음은 조금 더 복잡한 문장을 분석해보도록 하자. 블록 주석과 문자열 등 다양한 스타일을 포함시켜 보았다. 분석결과만 간단하게 그림으로 보이면 다음과 같다.

어떻게 이런 결과가 나오는지는 직접 분석해보면 알 수 있다. 실제 출력되는 결과는 다음과 같다. 흑백으로 인쇄되기 때문에 색상이 보이지는 않으므로 직접 실행하여 확인해보기 바란다.

구문 분석을 하는 가장 핵심 함수인 ParseLine 함수에 대해 나름대로 자세하게 설명하고 분석해보았다. 하지만 난이도가 있는 함수라 이 설명을 읽고 분석기의 동작을 한 번에 다 이해한다는 것은 사실 굉장히 어려울 것이다. 원래 다른 사람이 만든 코드를 읽는다는 것이 쉽지 않은 일인데다가 이 함수는 한눈에 들어올 정도로 깔끔하게 작성되어 있지도 않다. 세세한 부분까지는 정확하게 다 모르겠지만 대충 감은 잡았다는 생각이 들 정도면 일단은 충분하다.

이런 코드를 정확하게 분석해보고자 한다면 디버거를 적극 활용하기 바란다. 예제 문장을 입력해놓고 ParseLine이 어떤 순서로 pInfo에 정보들을 작성해 나가는지, 중간 정보들을 어떻게 관리하는지를 따라 해보기 바란다. 디버거로 코드를 쫓아 다니는 작업은 시간이 좀 많이 걸리는 대단히 지겨운 작업이기는 하지만 투자한 시간만큼 많은 것을 알려줄 것이다. 컴퓨터가 어떤 식으로 생각하고 판단하는지를 낱낱이 들여다 볼 수 있기 때문이다.