Notice
Recent Posts
Recent Comments
Link
«   2026/09   »
1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30
Archives
Today
Total
관리 메뉴

닌자고양이

[C/C++] 숫자 자릿수 콤마 표시하기 본문

C C++

[C/C++] 숫자 자릿수 콤마 표시하기

닌자고양이 2026. 5. 5. 17:28

 

위 처럼 3자리 마다 콤마를 추가하는 기능으로

최대한 간결하고 성능을 극대화 한 함수를 만들었다.

#include <string>
using namespace std;

string comma(int n)
{
    string s = to_string(n);

    for (int i = s.size(), j = n < 0; (i -= 3) > j;)
        s.insert(i, 1, ',');
        
    return s;
}

 

콘솔 출력 예시:

cout << comma(123456) << endl;
printf("%s\n", comma(123456).data());

 

빠른 성능

위의 insert 방식은 여러 문자의 메모리 이동이 콤마 개수만큼 일어나고 경우에 따라 메모리 재할당도 일어나서 언뜻 최적의 성능은 아닐 것처럼 보인다.

 

하지만 대부분의 경우 13자리(1조)보다 작은 수가 압도적으로 많이 사용되는데, 12자리 숫자까지는 콤마를 추가해도 "123,456,789,012" 로 15문자이며, string의 기본 스택 버퍼(MSVC기준 16) 내에서 이뤄지므로 재할당은 일어나지 않는다.

 

또한 string 생성시에 힙이 아닌 기본 스택 버퍼에 문자열을 생성하므로 매우 빠르고, memmove 도 내부적으로 8바이트씩 SIMD 명령어로 처리하므로 16자리까지의 메모리 이동은 4번의 명령과 L1캐시로 5클럭 이하로 처리된다.

 

 

64비트 정수 범위로 늘리고 자릿수 간격(3)과 콤마 문자(,)를 바꿀 수 있는 옵션을 추가:

 

string comma(long long n, int digits = 3, char sep = ',')
{
    string s = to_string(n);

    for (int i = s.size(), j = n < 0; (i -= digits) > j;)
        s.insert(i, 1, sep);

    return s;
}

 

 

템플릿화하고, 진법을 바꿀 수 있도록 수정해 본다.

다소 복잡한데 진법에 따라 큰 버퍼가 필요하면 힙이 할당될 수 있다.

template<class T>
string comma(const T n, int digits = 3, char sep = ',', int radix = 10)
{
    string s(radix >= 10 ? sizeof(T) * 4 - 1 : sizeof(T) * 16 + 2, '\0');  // 10진수 32비트이면 힙할당 안하게.
    s.resize(to_chars(s.data(), s.data() + s.size(), n, radix).ptr - s.data());

    for (int i = s.size(), j = n < 0; (i -= digits) > j;)
        s.insert(i, 1, sep);

    return s;
}

 

Comments