2015-03-03 67 views
1

我想將包含重音的字符串轉換爲C++中的純ASCII字符串(用於編制索引)。我知道這個問題已被問過無數次,但與其他人不同,我沒有選擇加入任何第三方庫,如ICU甚至使用boost。在沒有ICU或boost的C++中規範unicode字符?

到目前爲止,我已經嘗試創建地圖重音符號,以標準化的字符(無符號字符爲unsigned char)像下面

map<unsigned char, unsigned char> myMap; 
myMap['ì'] = 'i'; //few more like this 

,然後這個功能

string result; 
for(size_t i = 0; i < inputString.size(); i++) { 
    if(myMap.count(inputString[i]) > 0) { 
     result += myMap[inputString[i]]; 
    } else { 
     result += inputString[i]; 
    } 
} 

但是當我嘗試它像「Forlì」這樣的字符串,它會返回我Forl<C3>i。爲什麼?我怎樣才能刪除這個額外的<C3>

請注意,這將是生產級別的代碼,所以我將避免包括這樣一個小的變化(只是重音字符的情況下可由unsigned char表示)的重類。

+0

我想提醒一下,ICU和Boost C++庫都是免費且開源的。這意味着您可以隨時隨地獲取源文件,並查看它們是如何執行的。當我試圖「重新發明輪子」時,這總是適用於我。 – Drop 2015-03-03 06:00:06

+0

我實際上試過包括他們,但ICU給我垃圾(???)charcters而不是規範化的值,並且總是有許可問題。此外,ICU不是開發者友好的,並且在這種情況下字符串類型之間存在大量不必要的轉換 – rockstarjindal 2015-03-03 06:04:50

+0

@rockstarjindal:如果您試圖在'unsigned char'中填充大約100K的Unicode字符,則垃圾是可預期的。 ''í''可能正常工作,但它不可能是Unicode。 – MSalters 2015-03-03 08:08:50

回答

0

也許你應該使用unsigned short作爲地圖的第一種類型。還要將源文件保存爲UTF16。

啊..用basic_string <char>,我不認爲這個代碼工作。

原始文本必須用UTF8或UTF16編碼。閱讀它作爲ASCII將引入C/C++標準庫字符集轉換。我懷疑C3發生在這一步。這種編碼處理可能會惡化這種情況。

實際上,Unicode只是65535的16位值。如果我們只瞄準像字符一樣的字母,正確的代碼轉換是非常可行的,恕我直言。但是如果我們將它作爲ASCII加載,我們必須知道C/C++ IO如何處理代碼轉換。

兼容性,便攜性...非常複雜。這是許多人使用圖書館的ICU的原因之一。