我想创建一个有/没有线程安全的池。我不想定义一个互斥字段,如果池不是线程安全的,所以我使用了std::conditional,但是因为它没有完全按照我的要求做,并且创建了两个“type”选项,我选择了“int 8(char)”作为被动互斥类型。(相反,我希望整个定义都消失)
template<typename T, bool threadSafe = true>
class Pool
{
private:
//Mutex mutex; this is the field i want it to be DISAPPEARED, i modified it as below
std::conditional<threadSafe, Mutex, int8>::type mutex;
protected:
static constexpr item_type_size_datatype TypeSizeX = sizeof(T) + sizeof(size_t);
public:
Pool(size_t clusterItemCount) : ClusterItemCount(clusterItemCount),
ClusterByteSize(clusterItemCount* TypeSizeX)
{
#ifdef CriticalSection
if constexpr (threadSafe)
InitializeCriticalSection(&mutex);
#endif
}
~Pool()
{
Clear();
#ifdef CriticalSection
if constexpr (threadSafe)
DeleteCriticalSection(&mutex);
#endif
}
T* Occupy(bool& outFirstTime)
{
if constexpr (threadSafe)
{
MutexLock(mutex);
}
//do the occupation
if constexpr (threadSafe)
{
MutexUnlock(mutex);
}
return result;
}
};
正如您所看到的,在方法内部,我使用了“constexpr if”,它的工作原理很有魅力,因为它禁用了整个代码块。
**主要问题:**是否有更好的方法来禁用整个定义,如“Mutex mutex;“std::conditional”以外的“
**附加问题:**我收到“int 8 mutex”的“uninitialized variable”警告,我必须使用“0”进行初始化..如何在编译时使用“std::conditional”方式进行初始化。
3条答案
按热度按时间k7fdbhmy1#
这可以通过模板专门化来实现,例如:
ujv3wf0j2#
正如另一个答案所说,你可以使用模板专门化来实现这一点,因为不幸的是,不可能使用
std::enable_if
来声明成员。为了使它不需要专门化整个类,从而重复定义和声明,您可以创建一个模板专用的容器结构体,这取决于您是否希望包含变量,然后使用此模板结构体作为成员:
jgwigjjp3#
另一种方法是将
Pool
作为基类,将线程安全的PoolSafe
作为派生类,并进行必要的专门化。