Wchar_t ve char arasında, komut satırında kendisine iletilen bir dizi yerel konum kullanılarak dönüştürmeyi sınayan basit bir program var. Yerel adın ve dönüştürülmeyen dizenin yazdırılmasıyla başarısız olan dönüşümlerin bir listesini verir.xlocale kırık?
Ben clang ve libC++ kullanarak yapıyorum. Anladığım kadarıyla, libC++ adlı yerel destek, OS X üzerinde xlocale kitaplığı tarafından sağlanır.
Bazı beklenmedik hataların yanı sıra, dönüştürmenin başarısız olduğu bazı durumlarda da göremiyorum.
İşte program. İşte
#warning call this program like: "locale -a | ./a.out" or pass \
locale names valid for your platform, one per line via standard input
#include <iostream>
#include <codecvt>
#include <locale>
#include <array>
template <class Facet>
class usable_facet : public Facet {
public:
// FIXME: use inheriting constructors when available
// using Facet::Facet;
template <class ...Args>
usable_facet(Args&& ...args) : Facet(std::forward<Args>(args)...) {}
~usable_facet() {}
};
int main() {
std::array<std::wstring,11> args = {L"a",L"é",L"¤",L"€",L"Да",L"Ψ",L"א",L"আ",L"✈",L"가",L""};
std::wstring_convert<usable_facet<std::codecvt_utf8<wchar_t>>> u8cvt; // wchar_t uses UCS-4/UTF-32 on this platform
int convert_failures = 0;
std::string line;
while(std::getline(std::cin,line)) {
if(line.empty())
continue;
using codecvt = usable_facet<std::codecvt_byname<wchar_t,char,std::mbstate_t>>;
std::wstring_convert<codecvt> convert(new codecvt(line));
for(auto const &s : args) {
try {
convert.to_bytes(s);
} catch (std::range_error &e) {
convert_failures++;
std::cout << line << " : " << u8cvt.to_bytes(s) << '\n';
}
}
}
std::cout << std::string(80,'=') << '\n';
std::cout << convert_failures << " wstring_convert to_bytes failures.\n";
}
İşte
en_US.ISO8859-15 : €
Euro karakter ISO 8859-15 charset bulunabileceğini ve yok beklenmemektedir çıktı bir örnek doğru çıktı
en_US.ISO8859-1 : €
en_US.US-ASCII : ✈
bazı örnekler Yani bu başarısız olmamalı.
İşte beklediğim ama
en_US.ISO8859-15 : ¤
en_US.US-ASCII : ¤
Bu ISO 8859-1 var ama kaldırılır ve ISO 8859-15 euro simgesini ile değiştirildi para birimi simgesi olduğunu almazlar çıktı örnekleridir. Bu dönüşüm başarılı olmamalı, ancak hiçbir hata bildirilmiyor. Bu durumu incelerken, her iki durumda da '¤', '¤' ISO 8859-1 gösterimi olan 0xA4'e dönüştürüldüğünü buluyorum.
Yalnızca libC++ aracılığıyla xlocale doğrudan kullanmıyorum. Mac OS X üzerinde xlocale sadece kötü yerel tanımları ile kırılmış mı? Düzeltmenin bir yolu var mı? Yoksa başka bir şeyin sonucunu gördüğüm konular mı?
tamamlandı. id 10935025 – bames53
Hala 10.8'de kırılmış görünüyor :(Belki de xlocale verilerine ulaşmanın ve el ile düzeltme yapmanın bir yolu var mı? – bames53
UTF-32'nin aslında OS X'deki tüm yereller tarafından wchar_t kodlaması olarak kullanılmadığı ortaya çıkıyor. Oldukça talihsiz olan, – bames53