problem with SFINAE applied to class methods

Discussion in 'C++' started by Peter Collingbourne, Jul 1, 2004.

  1. Hello

    I am trying to do some template metaprogramming involving enabling or
    disabling a method in a parameterised class based on some condition. I
    am trying to use the Boost enable_if mechanism to do this, using the
    SFINAE principle. Here is a simple example showing what I am trying to do:

    1 #include <iostream.h>
    2 #include <boost/utility/enable_if.hpp>
    3
    4 using namespace boost;
    5
    6 template <bool CanFoo> class A {
    7
    8 public:
    9 typename enable_if_c<CanFoo>::type foo() {
    10 cout << "Foo" << endl;
    11 }
    12
    13 };
    14
    15 int main(int argc, char** argv) {
    16 A<false> cant_foo;
    17 cant_foo.foo();
    18 A<true> can_foo;
    19 can_foo.foo();
    20 }

    In this example the foo method in the A class is supposed to only exist
    when the boolean template parameter is true, thus I expect only one
    compiler error to occur on line 17. However when compiling this code I
    get the following additional message from the compiler (gcc 3.2.2):

    traits.cc: In instantiation of `A<false>':
    traits.cc:16: instantiated from here
    traits.cc:9: no type named `type' in `struct boost::enable_if_c<false, void>'

    Obviously there is not meant to be a type 'type' in this struct, which
    is what SFINAE is all about! Is this a bug in the compiler or am I
    misunderstanding the principle? If so can someone suggest an alternative
    way to do what I want?

    Thanks
    --
    Peter
    Peter Collingbourne, Jul 1, 2004
    #1
    1. Advertising

  2. On Thu, 1 Jul 2004 16:31:42 +0000 (UTC), Peter Collingbourne
    <> wrote:

    > Hello
    >
    > I am trying to do some template metaprogramming involving enabling or
    > disabling a method in a parameterised class based on some condition. I
    > am trying to use the Boost enable_if mechanism to do this, using the
    > SFINAE principle. Here is a simple example showing what I am trying to
    > do:
    >
    > 1 #include <iostream.h>
    > 2 #include <boost/utility/enable_if.hpp>
    > 3
    > 4 using namespace boost;
    > 5
    > 6 template <bool CanFoo> class A {
    > 7
    > 8 public:
    > 9 typename enable_if_c<CanFoo>::type foo() {
    > 10 cout << "Foo" << endl;
    > 11 }
    > 12
    > 13 };
    > 14
    > 15 int main(int argc, char** argv) {
    > 16 A<false> cant_foo;
    > 17 cant_foo.foo();
    > 18 A<true> can_foo;
    > 19 can_foo.foo();
    > 20 }
    >
    > In this example the foo method in the A class is supposed to only exist
    > when the boolean template parameter is true, thus I expect only one
    > compiler error to occur on line 17. However when compiling this code I
    > get the following additional message from the compiler (gcc 3.2.2):
    >
    > traits.cc: In instantiation of `A<false>':
    > traits.cc:16: instantiated from here
    > traits.cc:9: no type named `type' in `struct boost::enable_if_c<false,
    > void>'
    >
    > Obviously there is not meant to be a type 'type' in this struct, which
    > is what SFINAE is all about! Is this a bug in the compiler or am I
    > misunderstanding the principle? If so can someone suggest an alternative
    > way to do what I want?
    >
    > Thanks


    I think you are misunderstanding the principle. SNIFAE only applies
    (AFAIK) to choice between alternative function templates (including member
    function templates). When choosing the function template the fact that one
    choice leads to a type error is not a problem, it just means that choice
    is not made.

    The following would seem to do what you want without using SNIFAE (or
    enable_if)

    #include <iostream>
    #include <boost/static_assert.hpp>

    using namespace boost;

    template <bool CanFoo>
    class A {

    public:
    void foo() {
    BOOST_STATIC_ASSERT(CanFoo);
    std::cout << "Foo" << std::endl;
    }

    };

    int main(int argc, char** argv) {
    A<false> cant_foo;
    //cant_foo.foo();
    A<true> can_foo;
    can_foo.foo();
    }


    Remove the comment from cant_foo.foo() and you get a compile error.

    john
    John Harrison, Jul 1, 2004
    #2
    1. Advertising

  3. Peter Collingbourne

    Howard Guest

    Man, I hate acronyms! What's "SFINAE"?

    (In the news business, most acronyms are spelled out the first time they're
    used in an article. IMO [in my opinion], that would be a good idea in the
    newsgroups as well. :))

    -Howard
    Howard, Jul 1, 2004
    #3
  4. Peter Collingbourne

    Jeff Flinn Guest

    "Howard" <> wrote in message
    news:eVXEc.172442$...
    >
    > Man, I hate acronyms! What's "SFINAE"?


    Substitution Failure Is Not An Error.

    > (In the news business, most acronyms are spelled out the first time

    they're
    > used in an article. IMO [in my opinion], that would be a good idea in the
    > newsgroups as well. :))


    In this case, (IMO) if you don't know what the acronym stands for you
    probably aren't going to be able to contribute. :)

    Jeff F
    Jeff Flinn, Jul 1, 2004
    #4
  5. Peter Collingbourne

    David Harmon Guest

    On Thu, 1 Jul 2004 14:01:25 -0400 in comp.lang.c++, "Jeff Flinn"

    >Substitution Failure Is Not An Error.


    >In this case, (IMO) if you don't know what the acronym stands for you
    >probably aren't going to be able to contribute. :)


    But if the poster would spell it out, somebody else reading might learn
    something.
    David Harmon, Jul 2, 2004
    #5
  6. Peter Collingbourne

    Jeff Flinn Guest

    "David Harmon" <> wrote in message
    news:...
    > On Thu, 1 Jul 2004 14:01:25 -0400 in comp.lang.c++, "Jeff Flinn"
    >
    > >Substitution Failure Is Not An Error.

    >
    > >In this case, (IMO) if you don't know what the acronym stands for you
    > >probably aren't going to be able to contribute. :)

    >
    > But if the poster would spell it out, somebody else reading might learn
    > something.


    I googled SFINAE the first time I saw the acronym. I think that's why the
    definition stuck with me. If I'd been spoon fed, who knows...

    Jeff F
    Jeff Flinn, Jul 2, 2004
    #6
  7. In article <opsagx7jcv212331@andronicus>, John Harrison wrote:
    > BOOST_STATIC_ASSERT(CanFoo);


    Thank you for the hint about static assertions - this enabled me to
    implement a solution to my problem.

    --
    Peter
    Peter Collingbourne, Jul 2, 2004
    #7
  8. Peter Collingbourne

    David Harmon Guest

    On Fri, 2 Jul 2004 08:01:48 -0400 in comp.lang.c++, "Jeff Flinn"
    <> wrote,
    >> But if the poster would spell it out, somebody else reading might learn
    >> something.

    >
    >I googled SFINAE the first time I saw the acronym. I think that's why the
    >definition stuck with me. If I'd been spoon fed, who knows...


    "Substitution Failure Is Not An Error" is sufficiently mysterious to
    begin with.
    David Harmon, Jul 4, 2004
    #8
  9. Peter Collingbourne

    Pete Becker Guest

    David Harmon wrote:
    >
    > On Fri, 2 Jul 2004 08:01:48 -0400 in comp.lang.c++, "Jeff Flinn"
    > <> wrote,
    > >> But if the poster would spell it out, somebody else reading might learn
    > >> something.

    > >
    > >I googled SFINAE the first time I saw the acronym. I think that's why the
    > >definition stuck with me. If I'd been spoon fed, who knows...

    >
    > "Substitution Failure Is Not An Error" is sufficiently mysterious to
    > begin with.


    Think of it as "now you see it, now you don't." Or, perhaps, NYSINYD.

    --

    Pete Becker
    Dinkumware, Ltd. (http://www.dinkumware.com)
    Pete Becker, Jul 4, 2004
    #9
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Petterson Mikael
    Replies:
    3
    Views:
    4,277
    Neal Gafter
    Oct 8, 2003
  2. christopher diggins

    SFINAE problem.

    christopher diggins, Sep 26, 2005, in forum: C++
    Replies:
    4
    Views:
    452
    christopher diggins
    Sep 26, 2005
  3. siddhu
    Replies:
    1
    Views:
    297
    Victor Bazarov
    May 17, 2007
  4. Oltmans
    Replies:
    6
    Views:
    340
    Terry Reedy
    Mar 11, 2009
  5. Kenneth McDonald
    Replies:
    5
    Views:
    312
    Kenneth McDonald
    Sep 26, 2008
Loading...

Share This Page