preg_replace($pattern, $replacement, $subject)는 문자열에서 정규 표현식의 모든 일치를 찾아 바꿉니다. preg_replace('/\s+/', ' ', $text)는 연속된 공백, 탭, 줄바꿈을 모두 공백 하나로 바꿉니다.
원래 문자열은 바뀌지 않으며, preg_replace()는 새 문자열을 반환합니다. \b는 단어 경계를 나타내므로 cats는 그대로 남습니다.
역참조: {1}, \1
치환 문자열에서 $1은 첫 번째 캡처 그룹이 일치한 것을, $2는 두 번째를, $0은 전체 일치를 뜻합니다. 일치한 텍스트를 재배열할 때 쓰세요.
치환 문자열은 작은따옴표로 쓰세요. 큰따옴표 안에서 "\1"은 8진 이스케이프(바이트 0x01)가 되고, "${1}"은 정의되지 않은 1이라는 변수로 읽히며 PHP 8.2부터 폐지 예정인 문자열 문법을 씁니다. 작은따옴표 안의 '\1'은 '$1'과 똑같이 동작하지만, 일반적인 표기는 $1입니다.
영숫자가 아닌 문자 제거하기
부정 문자 클래스 [^...]는 나열되지 않은 모든 것과 일치합니다. 이를 ''로 바꾸면 제거됩니다. 다른 언어의 텍스트에는 u 수식어와 함께 유니코드 클래스 \p{L}(모든 문자)과 \p{N}(모든 숫자)을 쓰세요. 그렇지 않으면 é, ü와 모든 일본어 문자가 지워집니다.
URL 슬러그 만들기
패턴 여러 개를 이어 쓰면 제목이 URL 슬러그가 됩니다. 먼저 소문자로 바꾸고, 영숫자가 아닌 문자의 연속을 하이픈 하나로 바꾼 다음, 양 끝의 하이픈을 제거하세요.
여러 패턴, limit과 count
$pattern과 $replacement는 배열일 수 있습니다. 각 패턴이 같은 인덱스의 치환값으로 차례로 바뀝니다. 네 번째 인수는 패턴당 치환 횟수를 제한하고(-1은 제한 없음), 다섯 번째 인수는 치환한 횟수를 받습니다.
preg_replace_callback으로 치환값 계산하기
치환값이 일치한 내용에 따라 달라진다면 preg_replace_callback()을 쓰세요. 일치마다 $matches 배열과 함께 함수를 한 번 호출하고, 함수가 반환한 것을 삽입합니다. 짧은 콜백은 화살표 함수로 한 줄에 쓸 수 있습니다.
여러 패턴에 각각 다른 함수가 필요하다면 preg_replace_callback_array()가 pattern => callback 쌍의 배열을 받습니다.
변수에서 온 치환 텍스트
치환 문자열의 $나 백슬래시는 의미가 있으므로, 사용자나 데이터베이스에서 온 치환값이 망가질 수 있습니다. $10이라는 가격은 존재하지 않는 10번 그룹의 참조로 읽혀 빈 값이 됩니다.
찾는 텍스트도 치환값도 패턴이 아니라면 str_replace()가 더 간단하고 빠른 선택입니다. 아무것도 바꾸기 전에 패턴을 시험하려면 preg_match()를 참고하세요.
자주 묻는 질문
preg_replace에서 역참조를 쓰려면 어떻게 하나요?
치환 문자열에서 캡처 그룹을 $1, $2(또는 \1)로 참조하세요: preg_replace('/(\d{4})-(\d{2})-(\d{2})/', '$3/$2/$1', '2026-03-14')는 "14/03/2026"을 반환합니다. 치환 문자열은 작은따옴표로 쓰고, 참조 바로 뒤에 숫자가 오면 ${1}을 쓰세요.
PHP에서 영숫자가 아닌 문자를 모두 제거하려면 어떻게 하나요?
preg_replace('/[^a-zA-Z0-9]/', '', $s)는 ASCII 문자와 숫자만 남깁니다. 모든 언어의 문자(é, ü, 日本語, 한글)를 남기려면 u 수식어와 유니코드 클래스를 쓰세요: preg_replace('/[^\p{L}\p{N}]/u', '', $s).
preg_replace와 preg_replace_callback의 차이는 무엇인가요?
preg_replace()는 $1 자리 표시자가 든 고정된 치환 문자열을 받습니다. preg_replace_callback()은 일치마다 함수를 호출하고 그 반환값을 쓰므로, 대문자로 바꾸거나 계산하거나 배열에서 찾는 등 치환값을 계산할 수 있습니다.
str_replace와 preg_replace 중 무엇을 써야 하나요?
고정된 텍스트를 바꿀 때는 str_replace()를 쓰세요. 더 빠르고 이스케이프가 필요 없습니다. 연속된 공백, 아무 숫자, 단어 경계처럼 바꿀 텍스트가 패턴을 따를 때 preg_replace()를 쓰세요.
preg_replace로 첫 번째 일치만 바꾸려면 어떻게 하나요?
네 번째 인수로 limit을 넘기세요: preg_replace('/\d+/', '#', 'a1 b2 c3', 1)은 "a# b2 c3"를 반환합니다. 참조로 넘기는 다섯 번째 인수는 치환한 횟수를 받습니다.