我目前有以下代码:
template< class Obj, class ObjResult >
CLStatus convertObjToResult2( const Obj & xFrom, ObjResult & xTo )
{
CLStatus eStatus = CLSTATUS_SUCCESS;
switch ( xTo.eType )
{
case CEPTFull:
xTo.xData.xFull = xFrom;
break;
case CEPTBrief:
eStatus = Convert( xFrom, xTo.xData.xBrief );
break;
default:
eStatus = CLSTATUS_INVALIDPROJECTIONTYPE;
}
return eStatus;
}
template< class Obj, class ObjResult >
CLStatus convertObjToResult1( const Obj & xFrom, ObjResult & xTo )
{
CLStatus eStatus = CLSTATUS_SUCCESS;
switch ( xTo.eType )
{
case CEPTFull:
xTo.xData.xFull = xFrom;
break;
default:
eStatus = CLSTATUS_INVALIDPROJECTIONTYPE;
}
return eStatus;
}
所有ObjResults都有一个xFull
,但只有一些有xBrief
,其中xData是union
。这导致我在上面写了两个不同的模板,但如果我能以某种方式只有一个模板那就太棒了。
我不能简单地使用convertObjToResult2
,因为它无法使用没有xBrief
的对象类型进行编译。我查看了this answer,看看它是否会有所帮助,但我根本不了解它在做什么。
答案 0 :(得分:2)
自Logger logger = LogManager.GetCurrentClassLogger()
does not and won't have C++
功能以来,您需要解决此问题。
如果你不能像评论中所说的那样重载static if
,我想到了它上面的一个层,可以根据Convert
是否有成员而专门化。
ObjResult
std::void_t尚未成为标准的一部分,但实现很简单,可以在链接页面上找到。请确保不要在template <class Obj, class ObjResult, class = void>
struct ConvertIfHasBrief {
static auto Convert(Obj const &, ObjResult &) -> CLStatus {
return {};// dymmy value, not used
}
};
template <class Obj, class ObjResult>
struct ConvertIfHasBrief <Obj, ObjResult,
std::void_t<decltype(std::declval<ObjResult>().xData.xBrief)>> {
static auto Convert(Obj const &xFrom, ObjResult &xTo) {
return ::Convert(xFrom, xTo.xData.xBrief);
}
};
template< class Obj, class ObjResult>
CLStatus convertObjToResult( const Obj & xFrom, ObjResult & xTo )
{
CLStatus eStatus = CLSTATUS_SUCCESS;
switch ( xTo.eType )
{
case CEPTFull:
xTo.xData.xFull = xFrom;
break;
case CEPTBrief:
eStatus = ConvertIfHasBrief<Obj, ObjResult>::Convert(xFrom, xTo);
break;
default:
eStatus = CLSTATUS_INVALIDPROJECTIONTYPE;
}
return eStatus;
}
命名空间声明它。