이 글에서는 C++의 원시 문자열 리터럴(Raw String Literal)이 무엇인지, 어떤 의미를 가지는지 예제와 함께 자세히 알아보겠습니다.
원시 문자열 리터럴이란?
C++에는 줄 바꿈을 뜻하는 "\n", 탭을 뜻하는 "\t" 같은 이스케이프 문자(escape character)가 있습니다. 일반 문자열에서 이스케이프 문자를 출력하려고 하면 문자 자체가 아닌 해당 기능(줄 바꿈, 탭 등)이 실행되기 때문에 화면에 그대로 표시되지 않습니다.
이스케이프 문자를 있는 그대로 출력 화면에 보여주고 싶다면 R"(이스케이프 문자가 포함된 문자열)" 형태의 원시 문자열 리터럴을 사용하면 됩니다. 문자열 앞에 R을 붙이면 내부의 이스케이프 문자가 해석되지 않고 그대로 출력됩니다.
예제 1: 줄 바꿈 문자(\n)
다음 예제를 통해 원시 문자열 리터럴의 동작을 확인해 보겠습니다.
#include <iostream>
using namespace std;
int main(){
string str = "tutorials\npoint\n";
// 원시 문자열
string str_R = R"(tutorials\npoint\n)";
cout << "String is: " << str << endl;
cout << "Raw String is: " << str_R;
return 0;
}
출력 결과
위 코드를 실행하면 다음과 같은 결과가 출력됩니다.
String is: tutorials
point
Raw String is: tutorials\npoint\n
일반 문자열 str에서는 \n이 줄 바꿈으로 해석되어 "tutorials"와 "point"가 서로 다른 줄에 출력된 반면, 원시 문자열 str_R에서는 \n이 문자 그대로 화면에 표시되는 것을 확인할 수 있습니다.
예제 2: 탭 문자(\t)
#include <iostream>
using namespace std;
int main(){
string str = "tutorials\tpoint\t";
// 원시 문자열
string str_R = R"(tutorials\tpoint\t)";
cout << "String is: " << str << endl;
cout << "Raw String is: " << str_R;
return 0;
}
출력 결과
위 코드를 실행하면 다음과 같은 결과가 출력됩니다.
String is: tutorials point
Raw String is: tutorials\tpoint\t
일반 문자열에서는 \t가 탭 간격으로 실행된 반면, 원시 문자열에서는 \t가 그대로 출력되었습니다.
참고: 구분자(Delimiter) 사용하기
원시 문자열 안에 )" 패턴이 포함되어 있으면 문자열이 잘못 종료되어 컴파일 오류가 발생할 수 있습니다. 이런 경우에는 임의의 구분자를 추가하여 문제를 해결할 수 있습니다.
string str = R"*(문자열 안에 )" 가 포함되어도 안전)*";
R"d(...)d" 형식처럼 여는 괄호 앞뒤에 동일한 구분자를 넣으면, 문자열 중간에 닫는 괄호와 따옴표 조합이 나타나더라도 문자열이 중단되지 않습니다.
원시 문자열 리터럴의 활용 사례
- 정규표현식(Regex):
"\\d+"대신R"(\d+)"로 작성하면 백슬래시 중복을 피할 수 있습니다. - Windows 파일 경로:
"C:\\Users\\name"대신R"(C:\Users\name)"으로 간결하게 표현할 수 있습니다. - JSON, XML 등 문자열 데이터: 이스케이프 처리 없이 원본 그대로 유지해야 하는 경우에 유용합니다.
마무리
원시 문자열 리터럴은 이스케이프 문자를 해석하지 않고 문자열을 있는 그대로 다룰 수 있게 해주는 기능으로, C++11부터 도입되었습니다. 정규표현식이나 파일 경로처럼 백슬래시가 많이 사용되는 문자열을 다룰 때 코드의 가독성을 크게 높여주므로, 상황에 맞게 적극적으로 활용해 보시기 바랍니다.