我在我的代碼庫中有幾個「資源」。它們都是類,除了一個類共享相同的接口外,ShaderProgram只有一種方式,它需要兩個字符串作爲頂點和片段文件的文件名。這可以通過模板專業化解決,如果不是,那麼如何?
我有一個叫ResourceManager的模板類,處理所有這些資源除了着色器之一,因爲它需要兩個文件和其他人需要一個,我可以解決這個用模板特殊化?它需要是ResourceManager看到GetOrLoadFromFile(字符串,字符串)而不是(字符串)版本,而其他人有相反的,他們看到(字符串)和不(字符串,字符串)。 AttemptLoad也需要治療。我如何爲此制定解決方案請包括代碼,我以前從未做過模板專業化。
template < class ResType > class ResourceManager
{
public:
ResourceManager(void);
~ResourceManager(void);
SmartPointer<ResType> GetOrLoadFromFile(const std::string & fileName);
//weak_ptr<ResType> GetResourceFromID(ResourceID & resID);
void DestroyResources();
void ReleaseResources();
void ReloadResources();
protected:
private:
SmartPointer<ResType> AttemptLoad(const std::string & fileName);
std::unordered_map<string, SmartPointer<ResType> > mResMap;
};
// Relevant methods (SNIPPED)
template < class ResType> SmartPointer<ResType> ResourceManager<ResType>::GetOrLoadFromFile(const std::string & fileName)
{
if (!mResMap.empty())
{
auto index = mResMap.begin();
auto end = mResMap.end();
while (index != end)
{
if (index->first == fileName)
{
return index->second;
}
++index;
}
}
return AttemptLoad(fileName);
}
template < class ResType > SmartPointer<ResType> ResourceManager<ResType>::AttemptLoad(const std::string & fileName)
{
SmartPointer<ResType> pRes(new ResType());
if (pRes->LoadFromFile(fileName))
{
mResMap.insert(std::make_pair(fileName, pRes));
return pRes;
}
else
{
LogFailure("Failed to load resource file " + fileName)
return SmartPointer<ResType>(nullptr);
}
}
這是一個好主意,我考慮做這樣的。 – EddieV223
這是不是有可能調用的ResourceManager :: AttempLoad(常量LoadConfiguration),這是一個字符串類?在你的例子中沒有任何東西可以阻止它。 –
EddieV223
這個想法是爲AttempLoad嘗試執行正確類型的LoadConfiguration的dynamic_cast。是的,從某種意義上說,您正在從編譯時間檢查轉到運行時間檢查。但從另一個角度來說,傳遞LoadConfiguration而不是ExtendedLoadConfiguration應該像傳遞一個空的第二個字符串一樣被處理 - 可能並且應該很容易處理。我認爲標準和可擴展API的好處和舒適性比這個問題要大。 – Vadim