Попытка пропустить vtable и inline-вызов в случае, когда тип известен - PullRequest
3 голосов
/ 21 января 2020

Обновление: Похоже, это спецификация c до г cc <4,9, что улучшило девиртуализацию </a>.


В иерархии классов полиморфи c у меня есть не-виртуальная интерфейсная функция (назовем ее algorithm), которая вызывает некоторый (здесь для простоты только один) виртуальный метод (назовите его customization) из класса. Когда этот алгоритм вызывается для определенного c экземпляра производного класса, вызовы vtable не понадобятся, поскольку точный тип известен.

Теперь я закончил с таким вызовом во внутреннем l oop и хотел бы сделать его встроенным. Как этого достичь?

struct Base 
{
    inline virtual void customization(int i) {};
    inline void algorithm(int i) { customization(i); }
};

struct Derived : public Base
{
    // Adding this to every derived class instead of just the base will help, 
    // but is the kind of duplication I would like to avoid:
    // inline void algorithm(int i) { customization(i); }
    inline void customization(int i) override final { helper(i) };
};

void my_main()
{
    // Note that these are concrete instances, not references ..
    Derived d1, d2; 
    d1.algorithm(111);
    d2.algorithm(222);

    // ... which could just be optimized into the following, ...
    helper(111);
    helper(222);

    // ... but instead vtable calls to Base::algorithms result, behaving just as if it was
    static_cast<Base&>(d1).algorithm(111);
    static_cast<Base&>(d2).algorithm(222);
}

Следующие фрагменты из этого примера Годболта иллюстрируют это.

Фактический результат:

enter image description here

Желаемый результат:

enter image description here

...