与Java静态块等效的C ++习惯用法是什么?

与Java静态块等效的C ++习惯用法是什么?,第1张

与Java静态块等效的C ++习惯用法是什么? 您也可以在C ++中具有静态块-外部类。

事实证明,我们可以实现Java样式的静态块,尽管它是在类外部而不是在类内部,即在翻译单元范围内。内幕的实现有点丑陋,但是使用起来非常优雅!

可下载的版本

该解决方案现在有一个GitHub存储库,其中包含一个头文件:

static_block.hpp

用法

如果您写:

static_block {    std::cout << "Hello static block world!n";}

代码将在您的之前运行

main()
。您可以初始化静态变量,也可以执行其他任何 *** 作。因此,您可以在类的
.cpp
实现文件中放置这样的块。

笔记:

  • 必须 用花括号将静态块代码括起来。
  • 在C ++中不能保证执行静态代码的相对顺序。
实作

静态块实现涉及使用函数静态初始化的虚拟变量。您的静态块实际上是该函数的主体。为了确保我们不会与其他虚拟变量发生冲突(例如,来自另一个静态块或其他任何地方),我们需要一些宏机制。

#define ConCATENATE(s1, s2) s1##s2#define EXPAND_THEN_ConCATENATE(s1, s2) ConCATENATE(s1, s2)#ifdef __COUNTER__#define UNIQUE_IDENTIFIER(prefix) EXPAND_THEN_ConCATENATE(prefix, __COUNTER__)#else#define UNIQUE_IDENTIFIER(prefix) EXPAND_THEN_ConCATENATE(prefix, __LINE__)#endif // __COUNTER__

这是将内容组合在一起的宏工作:

#define static_block STATIC_BLOCK_IMPL1(UNIQUE_IDENTIFIER(_static_block_))#define STATIC_BLOCK_IMPL1(prefix)     STATIC_BLOCK_IMPL2(ConCATENATE(prefix,_fn),ConCATENATE(prefix,_var))#define STATIC_BLOCK_IMPL2(function_name,var_name) static void function_name(); static int var_name __attribute((unused)) = (function_name(), 0) ; static void function_name()

笔记:

  • 一些编译器不支持
    __COUNTER__
    -它不是C 标准的一部分;它不支持C 。在这种情况下,以上代码
    __LINE__
    也会使用。GCC和Clang支持
    __COUNTER__
  • 这是C 98;您不需要任何C 11/14/17构造。但是,即使不使用任何类或方法,它 也不是 有效的C语言。
  • __attribute ((unused))
    可被丢弃,或更换
    [[unused]]
    ,如果你有一个C ++编译器11,其不喜欢的GCC风格的未使用的扩展。
  • 这不会避免或不利于静态初始化顺序fiasco,因为虽然您知道静态块将在之前执行
    main()
    ,但不能保证相对于其他静态初始化确切的执行时间。

Live Demo



欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/zaji/5053778.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2022-11-15
下一篇2022-11-16

发表评论

登录后才能评论

评论列表(0条)

    保存