3

I want to write

struct Foo{
    MY_MACRO
};

and have that expand into

struct Foo{
    void bar(Foo&){}
};

How do I define MY_MACRO?

The only things I can come up with is the following:

#define MY_MARCO(X) void bar(X&){}
struct Foo{
    MY_MACRO(Foo)
};

This comes very close but is sub ideal, as I do not want to repeat the class name.

Unfortunately the following does not compile:

struct Foo{
    void bar(decltype(*this)&){}
};
B.S.
  • 1,435
  • 2
  • 12
  • 18
  • 1
    What about a template instead of a macro? – πάντα ῥεῖ Jan 31 '15 at 17:05
  • 2
    Generally, just **don't**. I did experiment once with a "NON_COPYABLE" macro, and tried out two different solutions, (1) passing the class name as macro argument, and (2) relying on an enclosing macro definition of "THIS_CLASS". But when the compilers caught up to speed, in particular Visual C++, the much better solution was to inherit from a non-copyable class. – Cheers and hth. - Alf Jan 31 '15 at 17:05
  • I'd strongly recommend using the [Curiously Recurring Template Pattern](http://stackoverflow.com/questions/4173254/what-is-the-curiously-recurring-template-pattern-crtp) instead. Macros are evil. – Zyx 2000 Jan 31 '15 at 19:10

2 Answers2

1

This is closely related this question. The answer is that you can not (yet) write something that uses the type of the class definition you are in. You will have to write a macro that includes the start of the class definition (i.e the struct Foo) and some mechanism to facilitate the typedef.

Community
  • 1
  • 1
Arne Mertz
  • 24,171
  • 3
  • 51
  • 90
1

But you can use decltype(*this) in a static_assert. I.e.:

#include <type_traits>

struct Foo {
    template <typename T>
    void bar(T& t) {
        static_assert(std::is_same<T&, decltype(*this)>::value,
                    "bar() only accepts objects of same type");
    }
};
myaut
  • 11,174
  • 2
  • 30
  • 62
  • Using a template is the only sane approach for this. I'd also suggest some research of mixins and CRTP to @B.S.. Using the C++ type system is far superior to using an ancient text replacement tool, which is what the preprocessor is. – Ulrich Eckhardt Jan 31 '15 at 17:50