gpt4 book ai didi

带有类模板参数的 C++ static_assert

转载 作者:行者123 更新时间:2023-11-28 04:35:11 25 4
gpt4 key购买 nike

我想做一些static dispatch的工作,让基类static_cast this指针指向派生类并调用同名函数来实现多态。我还想用 static_assert 来确保派生类确实重载了特定功能(否则会死循环)。我尝试将 static_assert 放在三个位置,但令人惊讶地发现并非所有位置都有效。

#include <iostream>

template<typename Type, Type Ptr>
struct MemberHelperClass;

#define DEFINE_HAS_MEMBER_FUNCTION(func) \
template<typename T, typename Type> \
static char MemberHelper_##func(MemberHelperClass<Type, &T::func>*); \
template<typename T, typename Type> \
static int MemberHelper_##func(...); \
template<typename T, typename Type> \
struct has_member_##func { \
static constexpr bool value = sizeof(MemberHelper_##func<T, Type>(nullptr)) == sizeof(char); \
};

#define STATIC_ASSERT_HAS_MEMBER_FUNCTION(T_, F_, func) \
static_assert(has_member_##func<T_, F_>::value == 1, "function `"#func"` is undefined or inaccessible"); \

template<typename D>
class B
{
public:
DEFINE_HAS_MEMBER_FUNCTION(f);

// 1.??? why this assert always fail even if D::f is present
// STATIC_ASSERT_HAS_MEMBER_FUNCTION(D, void(D::*)(), f);

void f() {
// 2.ok, assert fails only when B::f is called but D::f is not defined
// STATIC_ASSERT_HAS_MEMBER_FUNCTION(D, void(D::*)(), f);

static_cast<D*>(this)->f();
}

protected:
B() {
// 3.ok, assert fails only when instance of D is declared but D::f is not defined
// STATIC_ASSERT_HAS_MEMBER_FUNCTION(D, void(D::*)(), f);
}
};

class D : public B<D>
{
public:
// void f() { std::cout << __PRETTY_FUNCTION__ << std::endl; }
};

template<typename T>
void g(B<T>* pB)
{
pB->f();
}

int main()
{
D d;
g(&d); // should print void D::f()
return 0;
}

那么为什么第一个 static_assert 总是失败?我认为这将是最佳选择,因为不需要调用 f。此外,类 D 只需要声明,不需要 D 的实例...

最佳答案

当时B<D>的定义被隐式实例化,D不完整。因此,static_assert里面B的类定义在 D 的定义中看不到任何内容。 .成员函数体仅在使用时隐式实例化,此时D已经完成了。

class D : public B<D> // <--- B<D> implicitly instantiated here
{
public:
// void f() { std::cout << __PRETTY_FUNCTION__ << std::endl; }
}; // <--- D becomes complete here

关于带有类模板参数的 C++ static_assert,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51658509/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com