7

我需要一个 C 函数来返回格式化字符串的最终长度,这样我就可以正确分配目标字符串,而不是自己计算长度。在snprintf无法写入整个字符串的情况下,它会执行此操作,但不幸的是,它没有宽字符替代方案。

swprintf在出错的情况下返回 -1,而不是所需的长度(为什么不一样的行为?!?)

提到的标题asprintf似乎也没有帮助,因为它只提供了一个非宽版本。

_vscwprintf可以在 Windows 上使用,但我需要一个跨平台、标准版本或至少一个 Linux 版本,我将 #ifdef 代码。

有任何想法吗?谢谢!

4

3 回答 3

3

POSIX 2008 添加了open_wmemstream与 一起vfwprintf完全满足您需要的功能。它以前是一个 GNU 扩展,所以它在 GNU 系统上已经存在很长时间了。

这可以很容易地用于构造awprintf包装器。

于 2011-01-26T21:16:41.693 回答
3

是的,swprintf。请注意,尽管它的名称swprintf是宽字符,但它与snprintf, not sprintf等价,因为它将缓冲区大小作为其第二个参数;(幸运的是)没有不占用缓冲区大小的宽字符版本。

此外,由于它在溢出时返回 -1,因此您必须以其他方式获取字符串的总长度。唯一真正可移植的方法是从一定大小的缓冲区开始,尝试格式化并查看它是否足够大,如果没有,则增加大小并重新格式化,直到它足够大。正如您可以想象的那样,这不是很有效。

于 2011-01-26T20:14:39.007 回答
2

好吧,您的期望似乎存在根本缺陷。把这些加起来:

  1. Windows 有你想要的
  2. Linux 有一个非广泛的变体(asprintf不在任何标准中,而纯粹是 Linux 和 *BSD 的 GNU 扩展)。
  3. POSIX 将所有与字符串/文件相关的内容定义为一个以空字符结尾的char*数组,这解释了几乎所有 POSIX 函数都缺乏宽版本。
  4. 除了 2、3 和 4 之外,所有现代 Linux 发行版都是基于 UTF-8 的,这意味着非宽版本是“打算使用的”。

把这些加起来给出:你为什么需要这样的东西?当然,您不是wchar_t在 Unix 上使用 s 吗;)?如果是,还有两种选择:切换到类似tchar的解决方案(依赖于平台的 typedef)或完全切换到 UTF-8。

于 2011-01-26T20:10:58.870 回答