C++ C++;获取模板参数包中的第一个参数值
我有这门课C++ C++;获取模板参数包中的第一个参数值,c++,c++11,C++,C++11,我有这门课 class AssetManager { private: std::unordered_map<const std::type_info*, Asset*> assets; public: AssetManager(); virtual ~AssetManager(); template <typename T, typename ...Args> bool newAsset(Args... args) {
class AssetManager
{
private:
std::unordered_map<const std::type_info*, Asset*> assets;
public:
AssetManager();
virtual ~AssetManager();
template <typename T, typename ...Args>
bool newAsset(Args... args)
{
//Get path
if(cached(path)) { return true; }
auto asset = new T{ std::forward<Args>(args)... };
assets[&typeid(*asset)] = asset;
return *static_cast<T*>(assets[&typeid(T)]);
}
bool cached(const std::string& path)
{
for(auto asset : assets) {
if(asset.second->getPath() == path) {
return true;
}
}
return false;
}
};
继承Asset的类可能有不同数量的参数,因此我试图捕获第一个参数的值,因为它将始终是一个std::string路径,正如您在Asset类构造函数中看到的那样。如果您的第一个参数始终是一个std::string,那么以这种方式声明它是非常有意义的。首先,它解决了这个问题。另一方面,它可以确保打电话的人永远不会弄错。如果您在资产的构造函数中也需要它,可以将它单独传递给该构造函数,也可以在那里声明它
template <typename T, typename ...Args>
bool newAsset(const std::string &path, Args&&... args)
{
//Get path
if(cached(path)) { return true; }
auto asset = new T{ path, std::forward<Args>(args)... };
assets[&typeid(*asset)] = asset;
return *static_cast<T*>(assets[&typeid(T)]);
}
模板
bool newAsset(const std::string&path,Args&&…Args)
{
//获取路径
if(缓存的(路径)){return true;}
auto asset=new T{path,std::forward(在“notes”下)。最好使用typeid.hash\u code()
。
- 将路径设为强制参数,现在您可以在执行
cached
查找时引用它
- 将路径和其余参数一起传递给
Asset
构造函数
模板
bool newAsset(const std::string&path,Args&&…Args)
{
if(缓存的(路径)){return true;}
auto asset=newt{path,std::forward(args)…};
资产[&typeid(*资产)]=资产;
返回*static_cast(资产[&typeid(T)]);
}
如果我告诉你只在args之前声明一个std::string参数,这是不是太简单了,因为它是强制性的?是的,这样做吧。否则你就无法强制执行人们选择在包中传递的内容。为什么要费心留着出错的可能性呢?建议bool newAsset(args&&…args)
以正确支持完美转发。如果没有&&
,您总是在复制参数。在遵循@ascheplers建议的同时,还将基于范围的循环更改为自动&
。顺便说一句,返回类型是可疑的,可能应该是T&
。返回*资产
也可以避免强制转换和不必要的extra抬起头来。我想我会坚持这个解决方案。谢谢:)
template <typename T, typename ...Args>
bool newAsset(const std::string &path, Args&&... args)
{
//Get path
if(cached(path)) { return true; }
auto asset = new T{ path, std::forward<Args>(args)... };
assets[&typeid(*asset)] = asset;
return *static_cast<T*>(assets[&typeid(T)]);
}
template <typename T, typename ...Args>
bool newAsset(const std::string& path, Args&&... args)
{
if(cached(path)) { return true; }
auto asset = new T{ path, std::forward<Args>(args)... };
assets[&typeid(*asset)] = asset;
return *static_cast<T*>(assets[&typeid(T)]);
}