我有一個這樣定義的模板類:
template<typename T> class C_SharedResource : public C_Instance
{
// ...
private:
std::shared_ptr<T> g_resource;
S_AutoDestructionData g_autoDestructionData{};
// ...
public:
C_SharedResource() {}
C_SharedResource(const T& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
C_SharedResource(const std::shared_ptr<T>& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
template<typename T2> C_SharedResource<T2> dynamic_cast_resource() const;
// ...
}
dynamic_cast_resource 的定義為:
template<typename T>
template<typename T2>
C_SharedResource<T2> C_SharedResource<T>::dynamic_cast_resource() const
{
T2* tempResourcePtr = dynamic_cast<T2*>(g_resource.get());
if (tempResourcePtr == nullptr)
{
return C_SharedResource<T2>();
}
// This lines causes the compiler error.
C_SharedResource<T2> tempSharedResource(std::dynamic_pointer_cast<T2>(g_resource), g_autoDestructionData);
return tempSharedResource;
}
該函式背后的想法是向下轉換存盤的共享指標,然后回傳具有適當派生型別的新構造的共享資源。
使用它的一個例子:
// C_ITransformEntityComponent publicly inherits from C_IEntityComponent, which is also virtual.
std::shared_ptr<C_ITransformEntityComponent> transformComponent = std::make_shared<C_ITransformEntityComponent>();
C_SharedResource<C_IEntityComponent> sharedTC_1(transformComponent);
C_SharedResource<C_ITransformEntityComponent> sharedTC_2;
C_SharedResource<C_ITransformEntityComponent> sharedTC_3 = sharedTC_1.dynamic_cast_resource<C_ITransformEntityComponent>();
但是這條線:
C_SharedResource<T2> tempSharedResource(std::dynamic_pointer_cast<T2>(g_resource), g_autoDestructionData);
編譯失敗,報錯:
Error C2664 'C_SharedResource<C_ITransformEntityComponent>::C_SharedResource(const T &,C_SharedResource<T>::S_AutoDestructionData)': cannot convert argument 1 from 'std::shared_ptr<C_ITransformEntityComponent>' to 'const T &'
我正在使用 Visual Studio 2022,將 C 標準設定為 C 20。
編輯:最小的可重現示例:
#include <iostream>
#include <memory>
class C_Instance
{
public:
virtual void some_func() {}
};
template<typename T> class C_SharedResource : public C_Instance
{
public:
struct S_AutoDestructionData
{
bool m_autoDestroyAllInstances = false;
bool m_transferAutoDestructionState = false;
};
private:
std::shared_ptr<T> g_resource;
S_AutoDestructionData g_autoDestructionData{};
public:
C_SharedResource() {}
C_SharedResource(const T& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
C_SharedResource(const std::shared_ptr<T>& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
template<typename T2> C_SharedResource<T2> dynamic_cast_resource() const;
void some_func() override {}
};
class C_IEntityComponent
{
public:
virtual void some_other_func() {}
};
class C_ITransformEntityComponent : public C_IEntityComponent
{
public:
void some_other_func() override {}
};
template<typename T>
template<typename T2>
C_SharedResource<T2> C_SharedResource<T>::dynamic_cast_resource() const
{
T2* tempResourcePtr = dynamic_cast<T2*>(g_resource.get());
if (tempResourcePtr == nullptr)
{
return C_SharedResource<T2>();
}
C_SharedResource<T2> tempSharedResource(std::dynamic_pointer_cast<T2>(g_resource), g_autoDestructionData);
return tempSharedResource;
}
int main()
{
std::shared_ptr<C_ITransformEntityComponent> transformComponent = std::make_shared<C_ITransformEntityComponent>();
C_SharedResource<C_IEntityComponent> sharedTC_1(transformComponent);
C_SharedResource<C_ITransformEntityComponent> sharedTC_2;
C_SharedResource<C_ITransformEntityComponent> sharedTC_3 = sharedTC_1.dynamic_cast_resource<C_ITransformEntityComponent>();
return 0;
}
uj5u.com熱心網友回復:
您會收到編譯器錯誤,因為struct S_AutoDestructionData它是嵌套型別:
template<typename T> class C_SharedResource : public C_Instance
{
public:
struct S_AutoDestructionData
{
bool m_autoDestroyAllInstances = false;
bool m_transferAutoDestructionState = false;
};
// ...
C_SharedResource(const T& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
// ^ C_SharedResource<T>::S_AutoDestructionData
C_SharedResource(const std::shared_ptr<T>& in_resource, S_AutoDestructionData in_autoDestructionData = { false, false });
// ^ C_SharedResource<T>::S_AutoDestructionData
// ...
};
所以,在這一行:
// T = C_IEntityComponent
// T2 = C_ITransformEntityComponent
C_SharedResource<T2> tempSharedResource(std::dynamic_pointer_cast<T2>(g_resource), g_autoDestructionData);
C_SharedResource<T2>的建構式期望 aC_SharedResource<T2>::S_AutoDestructionData作為第二個引數;當你通過一個C_SharedResource<T>::S_AutoDestructionData. 那些不是同一型別。
如果您從以下位置struct S_AutoDestructionData退出class C_SharedResource:
struct S_AutoDestructionData
{
bool m_autoDestroyAllInstances = false;
bool m_transferAutoDestructionState = false;
};
template<typename T> class C_SharedResource : public C_Instance
{
public:
// ...
};
struct S_AutoDestructionData將不再嵌套,您的代碼將編譯。
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/489107.html
下一篇:臨時繼承中忽略的虛方法
