简体   繁体   English

我可以在成员函数上使用boost :: enable_if吗?

[英]Can I use boost::enable_if on a member function?

I'm writing a template class, and I want to allow an additional method to exist only for a certain template type. 我正在编写模板类,我想允许另一种方法仅存在于某种模板类型。 Currently the method exists for all template types, but causes a compilation error for all other types. 目前,该方法适用于所有模板类型,但会导致所有其他类型的编译错误。

Complicating this is that it's an overloaded operator(). 使这更复杂的是它是一个重载的operator()。 Not sure if what I want to do is actually possible here. 不知道我想要做什么实际上是可能的。

Here's what I have now: 这就是我现在拥有的:

template<typename T, typename BASE>
class MyClass  : public BASE
{
public:

    typename T& operator() (const Utility1<BASE>& foo);
    typename T const& operator() (const Utility2<BASE>& foo) const;
};

I want the T& version always available, but the T const& version only available if Utility2<BASE> is valid. 我希望T&版本始终可用,但只有Utility2<BASE>有效时, T const&版本才可用。 Right now, both methods exist, but attempting to use the const version gives a weird compilation error if Utility2<BASE> is invalid. 现在,两种方法都存在,但如果Utility2<BASE>无效,则尝试使用const版本会产生奇怪的编译错误。 I'd rather have a sensible error, or even a "no such member function" error. 我宁愿有一个明智的错误,甚至是“没有这样的成员函数”错误。

Is this possible? 这可能吗?

EDIT : After reading through the boost docs, here's what I've come up with, and it seems to work: 编辑 :阅读了升级文档,这是我提出的,它似乎工作:

template<typename T, typename BASE>
class MyClass  : public BASE
{
public:

    typename T& operator() (const Utility1<BASE>& foo);

    template<typename U>
    typename boost::enable_if<boost::is_same<Utility2<BASE>, U>, T>::type const &
    operator() (const U& foo) const;
};

So that method doesn't exist unless someone tries to use it with Utility2, and they can only create a Utility2 if it's valid for that BASE type. 因此,除非有人试图将它与Utility2一起使用,否则它不存在,并且如果它对该BASE类型有效,则它们只能创建一个Utility2。 But when it's not valid for that BASE type, MyClass will not waste time creating the accessor method. 但是当它对BASE类型无效时,MyClass不会浪费时间创建存取方法。

Yes, this is possible, but not with the class template parameter directly. 是的,这是可能的,但不能直接使用类模板参数。 boost::enable_if can only be used with a template parameter on the method itself. boost::enable_if只能与方法本身的模板参数一起使用。 So, with a little typedef usage: 所以,使用一点typedef:

template<typename T, typename BASE>
class MyClass  : public BASE
{
public:
  typedef Utility2<BASE> util;

  typename T& operator() (const Utility1<BASE>& foo);

  template<typename U>
  typename boost::enable_if<boost::is_same<util, U>, T>::type const &
  operator() (const U& foo) const;
};

This works, because Utility2 can only be created from a certain BASE type. 这是有效的,因为Utility2只能从某种BASE类型创建。 So if the BASE type is something else, the const version of operator() won't exist. 因此,如果BASE类型是其他类型,则operator()的const版本将不存在。

So, it's a very minor thing. 所以,这是一件非常小的事情。 It doesn't gain me much. 它并没有让我受益匪浅。 But it was neat to do. 但这很干净。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM