2014-03-25 46 views
1

基於答案here對如何號碼用逗號格式化問題stringstream的時候,我使用下面的代碼:段錯誤imbueing自定義區域

#include <locale> 
#include <stringstream> 

namespace 
{ 

class comma_numpunct : public std::numpunct<char> 
{ 
    protected: 
    virtual char do_thousands_sep() const 
    { 
     return ','; 
    } 

    virtual std::string do_grouping() const 
    { 
     return "\03"; 
    } 
}; 

} 


/* Convert number to string using a comma as the thousands separator. */ 
string thousands(const int x) { 

    /* custom locale to ensure thousands separator is comma */ 
    comma_numpunct* comma_numpunct_ptr = new comma_numpunct(); 
    std::locale comma_locale(std::locale(), comma_numpunct_ptr); 

    stringstream ss; 
    ss.imbue(comma_locale); // apply locale to stringstream 
    ss << x; 

    /* garbage collection */ 
    delete comma_numpunct_ptr; 

    return ss.str(); 
} 

GDB提供了以下回溯:

Program received signal SIGSEGV, Segmentation fault. 
0x0000000000000021 in ??() 
(gdb) bt 
#0 0x0000000000000021 in ??() 
#1 0x00007ffff7701535 in std::locale::_Impl::~_Impl()() from /usr/lib/x86_64-linux-gnu/libstdc++.so.6 
#2 0x00007ffff770166d in std::locale::~locale()() from /usr/lib/x86_64-linux-gnu/libstdc++.so.6 
#3 0x000000000044b93e in thousands (x=358799) at ../globals_utilities.cpp:104 
#4 0x000000000045650d in main (argc=1, argv=0x7fffffffdf58) at ../main.cpp:67 

所以,問題是(我相信)我試圖釋放new的內存。但我不知道如何解決這個問題。 (我不能使用std::unique_ptr,因爲我並不總是使用C++ 11支持進行編譯。)

如何在不泄漏內存的情況下修復段錯誤?

+1

你不應該手動釋放內存。 'std :: locale'的析構函數會爲你做。 – 0x499602D2

+1

爲什麼不只是使用靜態對象?那麼不需要刪除任何東西。 – Deduplicator

+0

@ user4815162342仍然是sigfaults。 – synaptik

回答

2

您的問題是語言環境方面(numpunct)。如果通過構造函數將它傳遞給區域設置,並且該區域的引用爲零,則區域設置將刪除該構面。

你可以這樣做:

comma_numpunct(size_t refs = 0) 
: numpunct(refs) 
{} 

comma_numpunct* comma_numpunct_ptr = new comma_numpunct(1); 

或更好的省略:

// double delete 
// delete comma_numpunct_ptr; 

您可以省略面的分配:

string thousands(const int x) { 
    comma_numpunct numpunct(1); 
    std::locale comma_locale(std::locale(), &numpunct); 
    std::stringstream ss; 
    ss.imbue(comma_locale); 
    ss << x; 
    return ss.str(); 
} 

從22.3.1.1.2類場所::小

裁判參數構造函數用於生命週期管理。

- 對於參== 0時,實現執行刪除 的static_cast(F)(其中,f是一個指針刻面) 當包含小面的最後的區域設置對象被銷燬;對於 refs == 1,實現永遠不會破壞方面。