How to Place a MACro in a Namespace in C++

Is it possible to place a macro in a namespace in c++?

#define is a preprocessor directive. The macros are being replaced before anything else apart from removing comments (which means, before compilation). So at the time macros are replaced, the compiler knows nothing about your namespaces.

As other people state, in your case it will be fine. However, This is how you can get problems:

namespace A
{
void Assert_ (int condition, std::string message, std::string file, int line)
{
std::cout << "A";
}
#define Assert(a,b) Assert_(a, b, __FILE__, __LINE__)

}
namespace B
{
void Assert_ (int condition)
{
std::cout << "B";
}
#define Assert(a,b) Assert_(a)

}

int main(int argc, char *argv[])
{
A::Assert(0,"asdasd");
B::Assert(0,"asdasd");
}

So while it looks like the defines are "in the namespaces", they are not, and the last #define will be always be used, which in this case will lead to a compile-time error, because the code in main will be replaced by:

A::Assert(0);
B::Assert(0);

instead of

A::Assert(0,"asdasd", _FILE_, _LINE_);
B::Assert(0);

Declaring namespace as macro - C++

Probably not a best practice as it can be difficult to read compared to a vanilla namespace declaration. That said, remember rules don't always apply universally, and I'm sure there is some scenario where a macro might clean things up considerably.

"But I couldn't find the STL files including this. If it is not included, how it can be used?".

All files that use this macro include yvals.h somehow. For example <vector> includes <memory>, which includes <iterator>, which includes <xutility>, which includes <climits>, which includes <yvals.h>. The chain may be deep, but it does include it it some point.

And I want to clarify, this only applies to this particular implementation of the standard library; this is in no way standardized.

C++ - namespace via macro definition - how to use it in header

Although I would say this is not the optimal way to arrange things, I've seen worse and the solution to your problem is rather straightforward:

class Bar {

#ifdef GRAPHICS_NAMESPACE
GRAPHICS_NAMESPACE::
#endif
Foo foo;
}

If you insist on sticking with this design, you can clean this up, somewhat, by defining a 2nd macro:

#ifdef GRAPHICS_NAMESPACE
#define GRAPHICS_CLASS(x) GRAPHICS_NAMESPACE:: x
#else
#define GRAPHICS_CLASS(x) x
#endif

And then declare things along the lines of:

class Bar {
GRAPHICS_CLASS(Foo) foo;
}

Finally, if you insist on relying on the preprocessor for this kind of critical functionality, you may want to consider spending a little bit more time reading what your C++ book says on this topic. These are fairly basic, straightforward uses of the C++ preprocessor, which I expect should be fully explained in any introduction on what a C++ preprocessor is, and how it works.

C++ macros and namespaces

Macros are handled by the pre-processor, which knows nothing about namespaces.
So macros aren't namespaced, they are just text substitution. The use of macros really is discouraged, among other reasons because they always pollute the global namespace.

If you need to print out a message, and you need it to be namespaced, simply use an inline function. The code seems simple enough to be properly inlined:

namespace a
{
inline void MESSAGE_A(const char* message)
{
std::cout << message << std::endl;
}
}

Using a macro to replace using namespace ...;

Modern IDEs provide you with autofill and code snippets and all kind of trinkets to reduce tedious repetative typing. Now when you (or someone else) get to read the code, the ugliness reverses: what took little time to type can take a lot to read and understand. So if the only goal of using a macro is to reduce your keyboard activity, I suggest defining a code snippet in your IDE instead.

This being said, I see no actual danger of this macro breaking your code behaviour or something like that - it's just a question of style.

Why there set macro definition and namespace in C++ .h file?

Question #1

See Purpose of Header guards

Question #2

Consider the case where you are using libraries. And two libraries would both like to have a function named Push(). We could name them: LibraryFoo_Push(), and LibraryBar_Push(), or we could use namespaces. Namespaces have some additional benefits with lookups as well.

And see C++ When is it OK to extend the `std` namespace? for when you are allowed to add stuff to the std namespace.

Concat Macro argument with namespace

## is a token pasting operator, i.e. it should make a single token out of multiple bits of token and as the compiler says, ::Val isn't a single token, it's two tokens.

Why do you need think you need the second ## at all? What's wrong with this.

#define TEST(a) TN::Info get ## a () { return TN::a; }

C++ nested namespaces with a macro

You can do it much simpler with BOOST_PP_SEQ_FOR_EACH:

#define BOOST_PP_VARIADICS
#include <boost/preprocessor/variadic/to_seq.hpp>
#include <boost/preprocessor/seq/for_each.hpp>

#define OP(s, state, x) namespace x {
#define NS(...) BOOST_PP_SEQ_FOR_EACH(OP, , BOOST_PP_VARIADIC_TO_SEQ(__VA_ARGS__))

NS(foo, bar, baz)

This expands to

namespace foo { namespace bar { namespace baz {


Related Topics



Leave a reply



Submit