Crate korean_regex

Source
Expand description

§korean-regex

한글은 초성, 중성, 종성의 조합이기에 각각을 분리해 분석하거나 사용하는 것이 때때로 유용합니다.

korean-regex는 한글을 초성, 중성, 종성의 조합으로 사용할 수 있도록 합니다.

§Syntax

기본적으로 korean-regex는 한 글자 OR 문법의 확장입니다. 정규표현식의 다른 문법은 건드리지 않습니다.

우선 초성, 중성, 종성은 각각 []로 둘러싸인 뒤 :으로 분리됩니다. 예를 들어 아래의 예시처럼 [ㄱ:ㅏ:ㄱ]일 경우 초성에 , 중성에 , 종성에 이 각각 들어가 이 됩니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[각]", compile("[ㄱ:ㅏ:ㄱ]", order).unwrap().to_string());

한 파트에 두 개 이상의 문자를 적으면 각 가능한 경우의 수로 변환됩니다. 예를 들어 아래처럼 [ㄱㄴ:ㅏㅣ:ㄴ]일 경우 모든 경우의 수인 간긴난닌로 대체됩니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[간긴난닌]", compile("[ㄱㄴ:ㅏㅣ:ㄴ]", order).unwrap().to_string());

만약 해당 칸은 비워놓는다면 해당 자리는 어떤 것이든 받아들이겠다는 의미입니다. 예를 들어 [::ㅎ]은 ’종성이 인 모든 음소’를 의미합니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[갛갷걓걯...흏흫힇힣]", compile("[::ㅎ]", order).unwrap().to_string());

-을 통해 연속되는 음소를 대체할 수 있습니다.

이때 기본적으로 ㄱㄴㄷㄹ...아닌 ㄱㄲㄴㄷㄸㄹ...와 같은 사전순으로 match된다는 점을 주의해 주세요. 이는 중성과 종성도 동일합니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[간깐난단딴란]", compile("[ㄱ-ㄹ:ㅏ:ㄴ]", order).unwrap().to_string());
assert_eq!("[간갠갼걘건겐견곈곤관괜괸굔군권궨귄균근긘긴]", compile("[ㄱ:ㅏ-ㅣ:ㄴ]", order).unwrap().to_string());
assert_eq!("[간-갈]", compile("[ㄱ:ㅏ:ㄴ-ㄹ]", order).unwrap().to_string());

0은 해당 자리에 음소가 없다는 것을 의미합니다. 기본적으로 종성에 사용됩니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[가각간나낙난다닥단]", compile("[ㄱㄴㄷ:ㅏ:0ㄱㄴ]", order).unwrap().to_string());

하지만 특수하게 [*:0:0]이나 [0:*:0]과 같은 형태도 사용될 수 있습니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[ㄱㄲㄴㄷㄸㄹ]", compile("[ㄱ-ㄹ:0:0]", order).unwrap().to_string());
assert_eq!("[ㅏㅐㅑㅒㅓㅔㅕㅖㅗㅘㅙㅚㅛㅜㅝㅞㅟㅠㅡㅢㅣ]", compile("[0:ㅏ-ㅣ:0]", order).unwrap().to_string());

^을 이용하면 해당 음소에 match하고 싶은 문자 대신 match하기 싫은 문자를 지정할 수 있습니다. 예를 들어 초성이 이고 중성이 이면서 받침이 이 아닌 모든 음소는 [ㄱ:ㅏ:^ㄹ]로 표현할 수 있습니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[가-갇갉-갛]", compile("[ㄱ:ㅏ:^ㄹ]", order).unwrap().to_string());

만약 종성이 없는 문자를 match하고 싶다면 [*:*:0] 대신 [*:*] 문법을 사용할 수도 있습니다. 예를 들어 [ㄱㄴㄷ:ㅏㅣ:0][ㄱㄴㄷ:ㅏㅣ]로 대체될 수 있습니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[가기나니다디]", compile("[ㄱㄴㄷ:ㅏㅣ:0]", order).unwrap().to_string());
assert_eq!("[가기나니다디]", compile("[ㄱㄴㄷ:ㅏㅣ]", order).unwrap().to_string());

만약 별개로 몇 개의 글자를 match에 추가하고 싶다면 |를 그 뒤에 추가하면 됩니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[과구놔누돠두한abc]", compile("[ㄱㄴㄷ:ㅜㅘ|한abc]", order).unwrap().to_string());

한글에는 두 개 이상의 글자가 합쳐서 생성된 문자들이 있습니다. 이나 , 등이 그 예입니다. 만약 글자 입력기가 같은 문자를 입력하는 것을 지원하지 않거나, 미관상의 이유로 코드에서 피하고 싶다면 괄호를 사용해서 문자를 합칠 수 있습니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[곿괇궧궯뽟뽧쀇쀏]", compile("[ㄱ(ㅂㅂ):(ㅗㅏ)(ㅜㅔ):(ㄹㅂ)(ㄱㅅ)]", order).unwrap().to_string());

이 고유 문법이 적용되는 범위를 넘어서면 기본 정규 표현식과 같이 섞어 사용할 수 있습니다.

use korean_regex::*;
 
let order = Order::Default;
let pattern = compile(r"\b([아-잏][^ ]{0,2})\b", order).unwrap();
let input = "저기 양을 잡아먹는 이리 때가 오르막길을 타고 간다!";
let result: Vec<_> = pattern.find_iter(input).map(|m| m.as_str()).collect();
assert_eq!(vec!["양을", "이리"], result);

§Example

다른 문법과 합치면 다음과 같이 사용할 수 있습니다.

use korean_regex::*;

let order = Order::Default;
// 초성이 ㄱ이 아니고 그 뒤에 종성이 `ㅇ`인 모든 글자가 오며 그 다음 글자 바운더리 혹은 종성이 없는 문자가 있는 경우
let pattern = compile(r"[^ㄱ::][::ㅇ](\b|[:])", order).unwrap();
let result: Vec<_> = pattern
    .captures_iter("한글은 초성, 중성, 종성의 조합이기에 각각을 분리해 분석하거나 사용하는 것이 때때로 유용합니다.")
    .map(|captures| captures[0].to_string())
    .collect();
assert_eq!(vec!["초성", "중성", "종성의", "사용하"], result)

§Hyphen replacing

정규표현식의 [] 문법에는 연속되는 문자를 대체하는 - 문법이 있습니다.

만약 연속되는 문자가 세 개 이상 있다면 korean-regex에서도 -문법이 이용됩니다.

use korean_regex::*;

let order = Order::Default;
assert_eq!("[가-깋라-맇]", compile("[ㄱㄹ::]", order).unwrap().to_string());

Enums§

KoreanRegexError
korean-regex에서 나올 수 있는 모든 오류를 모아놓은 enum입니다.
Order
하이픈 구성 시 사용할 순서를 결정합니다.

Functions§

compile
한국어 regex가 담긴 패턴을 받아 Regex로 컴파일합니다.
compilestr
컴파일 결과를 Regex로 컴파일하는 대신 String 값으로 받습니다.
substitute
초성, 중성, 종성 자리에 들어갈 raw값을 받고 실제로 컴파일된 값을 내보냅니다.