当 constexpr 时,C++ 可变参数模板“不包含参数包”是否应该避免?

问题描述 投票:0回答:1

我正在使用一些 C++ 20 功能(例如折叠运算符)来在编译时获取变量

template
的大小。然后,如果没有提供模板,我会在
constexpr if
中使用此尺寸,以避免使用
variadic template

但是我仍然收到错误:


src/engine/inb/component.h:39:68: error: expected primary-expression before '>' token
   39 |                 swallowTemplateExpansion(i_addComponent<_Components>(inheritor)...);
      |                                                                    ^
src/engine/inb/component.h:39:80: error: expansion pattern '((((cosmic::ComponentHolder<_Child>*)this)->cosmic::ComponentHolder<_Child>::i_addComponent < <expression error>) > (inheritor))' contains no parameter packs
   39 |                 swallowTemplateExpansion(i_addComponent<_Components>(inheritor)...);
      |                                                                                ^~~

这告诉我编译器无论如何都会评估 else 语句?

constexpr
在编译时避免了这样的代码,所以它不应该给我这个错误。

这是代码:


template<typename _Child>
    struct ComponentHolder
    {
    private:
        std::vector<std::shared_ptr<Component<_Child>>> components{};
        int i_addComponent(_Child* inheritor)
        {
            components.push_back(std::make_shared<Component<_Child>>(inheritor));
            return 0;
        }
    public:
        template<typename... _Components>
        constexpr ComponentHolder(_Child* inheritor)
        {
            constexpr auto _Size = (sizeof(_Components) + ...);
            if constexpr (_Size == 0)
            {
                return;
            } 
            else {
                swallowTemplateExpansion(i_addComponent<_Components>(inheritor)...);
            }
        }
    };

并且

swallowTemplateExpansion
只是一个空白的消费者 void 函数:


template<typename... T>
    void swallowTemplateExpansion(T&&... x)
    {}

为什么我的

constexpr if
还在尝试解压
variadic template
当我告诉编译器如果它的大小为 0 时,不要解压
variadic template

提前感谢您的帮助!

c++ templates variadic-templates constexpr fold
1个回答
0
投票

我通过向

i_addComponent
函数提供模板参数解决了这个问题,这是一个非常愚蠢的错误。

template<typename _Component>
        int i_addComponent(_Child* inheritor)
        {
            components.push_back(std::make_shared<_Component>(inheritor));
            return 0;
        }

© www.soinside.com 2019 - 2024. All rights reserved.