0

我想知道是否有可能以及如何在 C++ 跨平台(C99,C++0x 独立)中实现snprintf?有没有这样的提升?(我想知道要替换的 C++ 习语是snprintf(4)什么?)

4

6 回答 6

6

std::ostringstream可以替代使用snprintf

char buf[1024];
snprintf(buf, 1024, "%d%s", 4, "hello");

相等的:

#include <sstream>

std::ostringstream s;
s << 4 << "hello";
// s.str().c_str(); // This returns `const char*` to constructed string.

还有boost::lexical_cast

std::string s = boost::lexical_cast<std::string>(4) +
                    boost::lexical_cast<std::string>("hello");
于 2012-02-04T16:01:19.027 回答
2

是的,有支持格式化字符串的 Boost Format 库。

于 2012-02-04T16:04:18.963 回答
1

您可能想查看Qt QString 类,它提供了一个格式函数,它以一种非常面向对象的方式处理您想要的内容。您当然可以复制并从中学习。

是的,在标记为 boost 的问题中提及 Qt 可能是禁忌,但这个问题似乎比这更笼统。

于 2012-02-04T16:01:24.567 回答
1

既然提到了 Boost,那么 Boost.Format 有什么问题吗?

于 2012-02-04T16:05:34.313 回答
0

一旦我需要snprintf在 Windows/Linux/HP-UX 上。我定义snprintf_safe并在 Linux/HP-UX 上使用了snprinf,在 Windows 上我使用了_snprintf. 我记得_snprintf如果存储数据所需的字节数超过允许的最大大小,那么写入 '\0' 的方法会有所不同。所以有必要处理。反正就是这样的宏:

#ifdef #WIN32
int snprintf_safe()
{
  // make use of _snprintf
}
#else
   #define snprintf_safe snprintf
#endif
于 2012-02-04T16:19:43.783 回答
0

std::ostringstreamstd::to_string(c++11) 作为替代方案,但如果您需要更好的性能解决方案而无需额外的副本,或者只有 C 而不是 C++,您可能需要做其他事情:

MSVC不支持C99,因此没有snprintf功能,只有他们自制的: _snprintf.

_snprintfMSVC和官方 C99 (gcc,clang)的区别snprintf

返回值:

  • MSVC:如果缓冲区大小不足以写入所有内容(不包括终止 null!),则返回 -1
  • GCC:如果缓冲区足够大,则返回将写入的字符数

写入字节:

  • MSVC:尽可能多写,如果没有空间就不要在最后写NULL
  • GCC:尽可能多地写,总是写终止NULL(例外:buffer_size=0)

有趣的%n微妙之处:如果您%n在代码中使用,MSVC 将使其未初始化!如果由于缓冲区大小太小而停止解析,则 GCC 将始终写入如果缓冲区足够大时将写入的字节数。

所以我的建议是mysnprintf使用vsnprintf/编写你自己的包装函数_vsnprintf,它给出相同的返回值并在两个平台上写入相同的字节(小心:%n更难修复)。

于 2014-02-21T08:55:31.050 回答