最终类的用例

Posted

技术标签:

【中文标题】最终类的用例【英文标题】:Use cases for final classes 【发布时间】:2013-05-24 09:02:26 【问题描述】:

我在 Herb Sutter 的 Guru of the Week redux 上阅读 comments 关于 virtual 函数的内容,最后看到他提到了这一点:

[...] “final 的使用比较少”——嗯,确实是这样。我不知道有多少,在标准化过程中,Bjarne 反复询问它解决的问题的示例以及应该使用它的模式,我不记得有任何突出的主要问题。我唯一知道的是,如果您要定义一个库模块(这还不是标准概念),那么将叶类设为 final 可以为编译器提供更多信息来去虚拟化调用,因为知道库之外的代码不会' t 进一步推导,但我不确定这些天在包括积极去虚拟化在内的整个程序优化存在的情况下有多重要。

该答案没有提供很多关于 final 在类上的用例的示例,我很想知道它可以真正解决哪些问题。你知道吗,还是 final 会成为一些晦涩难懂且几乎未使用的功能?

【问题讨论】:

相关博文here. 相关问题:***.com/questions/8824587/… 也相关:***.com/questions/11704406/… 【参考方案1】:

我发现我描述了一个有趣的不寻常用例here。简而言之,通过防止从类 int 类继承,您可以在将来的库版本中将其替换为内置类型,而不会有破坏用户代码的风险。

但更常见的例子是去虚拟化。如果将类标记为最终类,编译器可以应用某些运行时优化。例如,

struct Object 
  virtual void run() = 0;
  virtual ~Object() 
;

struct Impl final : Object

  void run() override 
;

void fun(Impl & i)

  i.run(); // inlined!

由于final 说明符,现在可以内联对i.run() 的调用。编译器知道不需要 vtable 查找。

【讨论】:

好吧,我正要说上面的链接已经在 cmets 中分享了,但我没有意识到它也是你自己的文章。【参考方案2】:

final 在为初始接口提供(某种)外观时可能很有用,子类更容易使用它。 考虑:

class IMovable 
  public:
    void GoTo(unsigned position) = 0;


class Stepper : public IMovable 
  public:
    void GoTo(unsigned position) final;
  protected:
    virtual void MoveLeft() = 0;
    virtual void MoveRight() = 0;


void Stepper::GoTo(unsigned position) 
  for(;current_pos < position; current_pos++) 
     MoveRight(); 
  
  for(;current_pos > position; current_pos--) 
     MoveLeft();
   
       

现在,如果您想从 Stepper 派生,您会看到应该覆盖 MoveRightMoveLeft,但不应该覆盖 GoTo

在这个小例子中很明显,但是如果 IMovable 有 20 个方法,而 Stepper 有 25 个,并且有默认实现,那么您可能很难弄清楚应该覆盖什么,不应该覆盖什么。我在硬件相关的库中遇到过这样的情况。但我不认为这是一个值得按标准解决的主要问题;)

【讨论】:

那不是声明class final! @Alex,你是对的。我注意到一个关于虚函数的短语,所以我错过了强调使类最终化,而不是函数。亲爱的 OP,我应该收回答案还是您也对最终功能感兴趣? @Steed 对不起,我对final 函数一点也不感兴趣;在问这个问题之前我就已经知道它们为什么存在^^"

以上是关于最终类的用例的主要内容,如果未能解决你的问题,请参考以下文章

Linux文件系统的用例建模

Python + Appium 已解决driver(session)在多个class之间复用,执行完一个类的用例,再次执行下个类的用例时不需要初始化

pytest 用例编写规则命令行执行用例用例执行的先后顺序

HttpRunner 跳过用例录制生成用例用例分层机制

设计模式 用例图之二

使用postman做接口自动化测试,如何设置执行某个用例前先执行指定的用例(除了用复制用例的方法)