Search code examples
c++g++c-preprocessorpreprocessor

g++ 4.8.5 : does not give a valid preprocessing token using ##


I have an error "does not give a valid preprocessing token" when i try to compile my program with G++ 4.8 in Linux . and i do not have error when i compile it in Solaris with CCSuntudio.

below my code :

#include <iostream>

#define func(type1,varname1) \
        cout << "ma var est "<<##varname1<<" et le type est "<<#type1; \
        cout <<endl;

using namespace std;

int main() {
  func("int", "area");
}

It work perfectly in CCSunStudio but not with G++

hello.hxx:2:23: error: pasting "<<" and ""area"" does not give a valid preprocessing token
  cout << "ma var est "<<##varname1<<" et le type est "<<#type1; \
                       ^
hello.cxx:7:1: note: in expansion of macro ‘func’
 func("int","area");
 ^

Thanks for any help


Solution

  • You do not need to use ## every time you use an argument in a macro.

    You only need that when you want to concatenate the argument with some other text, to form a single "token". For example, if you had "bo" and "ol" and wanted to make "bool".

    In this case, << and "area" should be distinct tokens. In fact, <<"area" would not be a valid token.

    Since your argument is a token in its own right, you literally just write it there in the code:

    #define func(type1,varname1) \
        cout << "ma var est " << varname1 << " et le type est " << #type1; \
        cout << endl;
    

    Tokens are almost words, but they're programming language words rather than English words. You can read more about tokens in a book or guide about parsers.

    (You may still need #type1, because that does something different: converting the argument into a stringised version of its value. However, since you're already passing a string "int", currently you don't need it there either.)


    It work perfectly in CCSunStudio

    Actually this means it doesn't work properly in Sun Studio!

    i do not have error when i compile it in Solaris with CCSunStudio.

    That appears to be because Sun Studio has a level of compatibility with antique K&R C, which did things a bit differently.

    You can use the -xtransition option to find other places where your code needs updating to be standard-compliant.