Search code examples
c++c++11user-defined-literals

What is the scope of a user-defined literal?


Consider these two:

namespace X1
{
    A operator "" _x(unsigned long long i) { return A{i}; }
};

namespace X2
{
    B operator "" _x(unsigned long long i) { return B{i}; }
};

The x literal is defined twice, but one of them is defined in namespace X1 while another is defined in namespace X2.

According to the C++ standard, can this code be compiled?


Solution

  • A user-defined literal is treated as a call to operator ""X(...) where X is an identifier (for example, _x) and the ... depends on the form of the user-defined literal. Lookup of the appropriate user-defined literal operator then proceeds according to the usual rules for unqualified lookup; [lex.ext]:

    2 - A user-defined-literal is treated as a call to a literal operator or literal operator template (13.5.8). To determine the form of this call for a given user-defined-literal L with ud-suffix X, the literal-operator-id whose literal suffix identifier is X is looked up in the context of L using the rules for unqualified name lookup (3.4.1). [...]

    The definitions of the _x literal only conflict if both definitions are made available for unqualified lookup by a using or using namespace declaration or by entering either namespace; the conflict is only problematic if a call to the unqualified operator is actually made.

    { using namespace X1; auto o = 5_x; }          // OK; o is of type A
    { using namespace X2; auto o = 5_x; }          // OK; o is of type B
    { using namespace X1; using namespace X2; }    // OK; operator "" _x is not used
    { using namespace X1; using namespace X2; auto o = 5_x; }  // ambiguous
    

    It would also be OK if the _x were different types of user-defined literal operators e.g. if one were an integer literal operator and the other a float literal operator.