p26001-store-acs-soc-fw-app/util/FactoryManager.h
2026-09-28 21:33:04 +08:00

79 lines
2 KiB
C++

#ifndef BE13A370_B199_43EC_A4E6_E2D4FD197D63
#define BE13A370_B199_43EC_A4E6_E2D4FD197D63
/*
*******************************************************************************
* INCLUDE
*******************************************************************************
*/
#include "ClassAssistant.h"
#include <map>
#include <Poco/SharedPtr.h>
#include <Poco/Format.h>
namespace Util
{
/*
*******************************************************************************
* CLASS DECLARE
*******************************************************************************
*/
template <class T> class SimpleSelector
{
public:
static T select(T val)
{
return val;
}
};
template <class T, class TKey, class TSelector, class... TArgs> class FactoryManager
{
private:
class IFactory
{
public:
using Ptr = Poco::SharedPtr<IFactory>;
virtual ~IFactory()
{
}
public:
virtual T* create(TArgs... args) = 0;
};
template <class C> class Factory: public IFactory
{
public:
C* create(TArgs... args) override
{
return new C(args...);
}
};
using Factories = std::map<TKey, typename IFactory::Ptr>;
public:
static T* create(TArgs... args)
{
TKey key = TSelector::select(args...);
if (_factories.find(key) == _factories.end())
throw Poco::NotFoundException(
Poco::format("FactoryManager: Factory '%s' does not exists.", Util::ClassAssistant::demangle<T>()),
-EINVAL);
return _factories[key]->create(args...);
}
template <class C> static void registerClass(TKey key)
{
_factories[key] = new Factory<C>();
}
private:
static Factories _factories;
};
template <class T, class TKey, class TSelect, class... TArgs>
typename FactoryManager<T, TKey, TSelect, TArgs...>::Factories FactoryManager<T, TKey, TSelect, TArgs...>::_factories;
}
#endif