我有一個數據庫類應該提供一個模板方法來返回代表表格的資源庫對象。每個存儲庫只能存在一次。我發現this的例子,但我想有一個內置的緩存。具有內置緩存的C++對象工廠 - 陰影模板參數
的database.h
頭看起來是這樣的:
class Database
{
public:
Database(const char *connectionString);
template<typename T> shared_ptr<class T : RepositoryBase> GetRepository();
private:
sqlite3* _connection;
map<string, RepositoryBase> _repositoryCache;
};
的GetRepository
方法類似於實現:
template<typename T> shared_ptr<class T : RepositoryBase> Database::GetRepository()
{
string name = typeid(T).name();
if(_repositoryCache.count(name) == 0)
{
_repositoryCache[name] = shared_ptr<T>(new T(_connection));
}
return _repositoryCache[name];
}
我想叫它像:
// SampleRepository is derived from RepositoryBase
shared_ptr<SampleRepository> sampleRepo = GetRepository<SampleRepository>();
當我編譯我得到的錯誤:
error : declaration of 'T' shadows template parameter
我需要在模板方法中更改以避免影響任何模板參數?
UPDATE
後NathanOliver的建議模板方法是這樣的:
template<typename T, typename enable_if<is_base_of<RepositoryBase, T>::value>::type* = nullptr> shared_ptr<T> Database::GetRepository()
{
string name = typeid(T).name();
if(_repositoryCache.count(name) == 0)
{
_repositoryCache[name] = shared_ptr<T>(new T(_connection));
}
return _repositoryCache[name]();
}
這一次,我得到的錯誤:
error : template parameter redefines default argument
它指向nullptr
在模板簽名。
更新2
我試過基於從@NathanOliver給出了答案參數的幾種組合。我仍然得到錯誤:
1>C:\..\Database.cpp(65,98): error : template parameter redefines default argument
1>template<typename T, typename std::enable_if<std::is_base_of<RepositoryBase, T>::value>::type* = nullptr> std::shared_ptr<T> Database::GetRepository()
1> ^
1>C:\..\Database.h(25,108) : note: previous default template argument defined here
1> template<typename T, typename std::enable_if<std::is_base_of<RepositoryBase, T>::value>::type* = nullptr> std::shared_ptr<T> GetRepository();
1> ^
爲了更好地理解,我還添加了存儲庫基類。
class RepositoryBase
{
public:
RepositoryBase(sqlite3* connection);
virtual string GetTableName() = 0;
protected:
sqlite3* _connection;
};
是'數據庫'模板?如果是的話,模板'部分是什麼樣子? –
NathanOliver
否。它只是您可以在數據庫頭文件中看到的「GetRepository」函數模板。 –
你想用'shared_ptr'來做什麼?你是否想說'T'需要從'RepositoryBase'派生? –
NathanOliver