是否有任何类型安全,编译时检查printf的实现?

时间:2017-11-09 10:25:46

标签: c++

我看到很多类型安全的printf实现,但是大多数都使用异常来引发类型错误。

作为练习,我使用字符串文字实现了类似printf的格式化原型,它似乎解决了旧的,良好的printf系列的所有问题(除了使用从外部源读取的格式,这总是不安全)。

示例:

int main(int argc, char* argv[])
{
    std::cout << "const char*: %s, std::string: %s\n"_format("ONE", std::string{"TWO"});
    std::cout << "user defined: %*\n"_format(std::complex<int>{1, 2});
    std::cout << "hex: 0x%x, int: %d\n"_format(16, 123);
    std::cout << "double.2: %.2f, double: %f\n"_format(13.123123, 12.1);

    std::string s = "p(%d, %d)\n"_format(123, 234);
    std::cout << s;

//    not yet working
//    int x, y;
//    std::cin >> "p(%d, %d)"_format(x, y);
//    "p(%d, %d)"_format(x, y) = "p(999, 888)";
}

完整,肮脏且不完整或优化的代码为here

生成的.s表示在运行时没有进行文本处理,即使变量不是const,而是从argv获取。传递错误的变量类型,或使用参数计数会导致丑陋的编译错误,这可以通过静态断言或概念进行改进。

这只是练习,问题是:是否有支持此类构造的库,以及为什么这种方法不是c ++标准的一部分?

2 个答案:

答案 0 :(得分:2)

有没有这样的图片?排序:GCC(和其他编译器)理解printf格式字符串的语法,如果类型不匹配,可以说服它发出编译时错误。

为什么这种方法不属于C ++?因为Bjarne最初提出了iostream,它也提供类型安全的IO,没有人对此有足够的感觉来提出另一个提案。

答案 1 :(得分:0)

{fmt} library具有编译时格式字符串检查。例如

#include <fmt/format.h>

int main() {
  std::string s = fmt::format(FMT_STRING("{:d}"), "hello");
}

给出了编译时错误,因为d是字符串的无效格式说明符。这使用类似Python的格式字符串语法,但不使用printf语法。