所以我终于回到了我的主要任务 - 将一个相当大的C ++项目从Windows移植到Mac。
直接我遇到了wchar_t在Windows上为16位但在Mac上为32位的问题。这是一个问题,因为所有字符串都由wchar_t表示,并且在Windows和Mac机器之间会有来回的字符串数据(在磁盘数据和网络数据形式中)。由于它的工作方式,在发送和接收数据之前将字符串转换为某种通用格式并不是完全简单的。
我们最近也开始支持更多语言,所以我们开始处理大量的Unicode数据(以及处理从右到左的语言)。
现在,我可能会在这里混淆多个想法,并为自己造成比需要更多的问题,这就是我提出这个问题的原因。我们认为将所有内存中的字符串数据存储为UTF-8非常有意义。它解决了wchar_t不同大小的问题,这意味着我们可以轻松支持多种语言,它还可以大大减少我们的内存占用(我们有很多 - 主要是英文 - 字符串加载) - 但似乎很多人都没有这个。有什么我们想念的吗?有一个明显的问题,你必须处理字符串长度可以小于存储该字符串数据的内存大小。
或者使用UTF-16更好的主意?或者我们应该坚持使用wchar_t并编写代码来在我们读/写磁盘或网络的地方转换wchar_t和Unicode之间的转换?
我意识到这对于征求意见非常危险 - 但是我们很担心我们忽略了一些显而易见的东西,因为它似乎没有很多Unicode字符串类(例如) - 但是还有很多代码用于转换为/来自Unicode,如boost :: locale,iconv,utf-cpp和ICU。
答案 0 :(得分:8)
在涉及文件或网络连接时,始终使用为字节定义的协议。不要依赖C ++编译器如何在内存中存储任何内容。对于Unicode文本,这意味着选择编码和字节顺序(好吧,UTF-8不关心字节顺序)。即使您当前想要支持的平台具有类似的架构,也可能会出现另一个具有不同行为的流行平台,甚至是现有平台的新操作系统,您会很高兴编写可移植代码。
答案 1 :(得分:2)
我倾向于使用UTF-8作为内部表示。您只会丢失字符串长度检查,但无论如何都不是很有用。对于Windows API转换,我使用自己的Win32转换函数I devised here。因为Mac和Linux是(对于大部分标准的UTF-8感知,不需要在那里转换任何东西)。你获得的免费奖金:
std::string
。答案 2 :(得分:1)
根据经验:UTF-16用于处理,UTF-8用于通信&存储
当然,任何规则都可以被打破,而且这个规则不是刻在石头上。 但你必须知道什么时候可以打破它。
例如,如果您使用的环境需要其他东西,那么使用其他东西可能是个好主意。但Mac OS X API使用UTF-16,与Windows相同。所以UTF-16更有意义。 在将所有内容放入网络之前进行转换(因为您可能在2-3个例程中执行)比执行所有转换以调用OS API更直接。
您开发的应用程序类型也很重要。 如果它是文本处理非常少的东西,并且对系统的调用非常少(类似于电子邮件服务器,大多数情况下都不会改变它们),那么UTF-8可能是一个不错的选择。
所以,就像你可能讨厌这个答案一样,“这取决于”。
答案 3 :(得分:1)
ICU有一个C ++字符串类,UnicodeString