C# 정규표현식(Regex) 실전 가이드: 패턴 매칭과 텍스트 처리
정규표현식(Regular Expression)은 입력 텍스트와 매칭될 수 있는 패턴입니다. .NET 프레임워크는 이러한 매칭을 수행하는 정규표현식 엔진을 제공합니다. 패턴은 하나 이상의 문자 리터럴, 연산자, 구성 요소로 이루어집니다.
정규표현식 정의를 위한 구성 요소
문자, 연산자, 구성 요소의 다양한 카테고리가 정규표현식 정의를 가능하게 합니다.
- 문자 이스케이프 (Character Escapes)
- 문자 클래스 (Character Classes)
- 앵커 (Anchors)
- 그룹화 구성 요소 (Grouping Constructs)
- 량화자 (Quantifiers)
- 역참조 구성 요소 (Backreference Constructs)
- 대안 구성 요소 (Alternation Constructs)
- 치환 (Substitutions)
- 기타 구성 요소 (Miscellaneous Constructs)
Regex 클래스
System.Text.RegularExpressions.Regex 클래스는 정규표현식을 나타냅니다. 주요 메서드:
| 번호 | 메서드 및 설명 |
| 1 | IsMatch(input) - 입력 문자열에서 패턴 매칭 여부 확인 (bool) |
| 2 | IsMatch(input, startat) - 지정된 시작 위치부터 매칭 확인 |
| 3 | IsMatch(input, pattern) - 정적 메서드로 패턴 매칭 확인 |
| 4 | Matches(input) - 입력 문자열에서 패턴의 모든 출현 검색 (MatchCollection 반환) |
| 5 | Replace(input, replacement) - 패턴 매칭 부분을 치환 문자열로 대체 |
| 6 | Split(input) - 패턴 위치에서 문자열 분할하여 배열 반환 |
참고: 전체 메서드/속성 목록은 Microsoft 공식 문서 참조.
자주 쓰는 정규표현식 패턴 속성
| 패턴 | 의미 |
.임의의 단일 문자 (줄바꿈 제외) |
\d숫자 (0-9) |
\D숫자가 아닌 문자 |
\w단어 문자 (영문자, 숫자, _) |
\W단어 문자가 아닌 문자 |
\s공백 문자 (스페이스, 탭, 줄바꿈) |
\S공백이 아닌 문자 |
^문자열/행 시작 |
$문자열/행 끝 |
*0회 이상 반복 |
+1회 이상 반복 |
?0회 또는 1회 반복 |
{n}정확히 n회 반복 |
{n,}n회 이상 반복 |
{n,m}n회 이상 m회 이하 반복 |
[abc]a, b, c 중 하나 |
[^abc]a, b, c가 아닌 문자 |
(abc)그룹화 및 캡처 |
(?:abc)비캡처 그룹 |
|또는 (대안) |
예제 1: 'S'로 시작하는 단어 매칭
using System;
using System.Text.RegularExpressions;
namespace RegExApplication
{
class Program
{
private static void ShowMatch(string text, string expr)
{
Console.WriteLine("패턴: " + expr);
MatchCollection mc = Regex.Matches(text, expr);
foreach (Match m in mc)
{
Console.WriteLine(m);
}
}
static void Main(string[] args)
{
string str = "A Thousand Splendid Suns";
Console.WriteLine("'S'로 시작하는 단어 매칭:");
ShowMatch(str, @"\bS\S*");
Console.ReadKey();
}
}
}
출력: Splendid, Suns
\b는 단어 경계, \S*는 공백이 아닌 문자 0회 이상을 의미합니다.
예제 2: 'm'으로 시작하고 'e'로 끝나는 단어 매칭
string str = "make maze and manage to measure it";
ShowMatch(str, @"\bm\S*e\b");
출력: make, maze, manage, measure
\b 단어 경계, m으로 시작, \S* 중간 문자들, e\b 'e'로 끝남.
예제 3: 여러 공백을 하나로 치환
using System;
using System.Text.RegularExpressions;
namespace RegExApplication
{
class Program
{
static void Main(string[] args)
{
string input = "Hello World"; // 여러 공백
string pattern = @"\s+"; // 하나 이상의 공백
string replacement = " "; // 단일 공백으로 치환
Regex rgx = new Regex(pattern);
string result = rgx.Replace(input, replacement);
Console.WriteLine("원본: '{0}'", input);
Console.WriteLine("치환: '{0}'", result); // "Hello World"
Console.ReadKey();
}
}
}
실전 활용 예제
이메일 유효성 검사
string emailPattern = @"^[^@\s]+@[^@\s]+\.[^@\s]+$";
bool isValid = Regex.IsMatch(email, emailPattern);
전화번호 추출 (한국 형식)
string phonePattern = @"01[016789]-?\d{3,4}-?\d{4}";
MatchCollection phones = Regex.Matches(text, phonePattern);
HTML 태그 제거
string cleanText = Regex.Replace(html, @"<[^>]+>", "");
날짜 파싱 (yyyy-MM-dd)
string datePattern = @"(\d{4})-(\d{2})-(\d{2})";
Match m = Regex.Match(input, datePattern);
if (m.Success)
{
int year = int.Parse(m.Groups[1].Value);
int month = int.Parse(m.Groups[2].Value);
int day = int.Parse(m.Groups[3].Value);
}
성능 팁
- 컴파일된 정규식: 반복 사용 시
RegexOptions.Compiled 옵션 사용
- 정적 메서드 활용: 일회성 사용은
Regex.IsMatch(input, pattern) 정적 메서드
- 타임아웃 설정:
new Regex(pattern, RegexOptions.None, TimeSpan.FromSeconds(1))로 무한 백트래킹 방지
- 캐싱: 자주 쓰는 Regex 인스턴스는 static readonly 필드로 캐싱
// 모범 사례: 컴파일된 정규식 캐싱
private static readonly Regex EmailRegex = new Regex(
@"^[^@\s]+@[^@\s]+\.[^@\s]+$",
RegexOptions.Compiled | RegexOptions.IgnoreCase,
TimeSpan.FromSeconds(1)
);
public bool IsValidEmail(string email)
{
return EmailRegex.IsMatch(email);
}
팁: 복잡한 정규식은 regex101.com 같은 도구로 테스트하며 작성하세요. 주석 모드(RegexOptions.IgnorePatternWhitespace)로 가독성 높여 작성도 가능합니다.