2

I would like to define a user-defined literal for shorts. Just like this:

short operator"" _s(int x) 
{ 
    return (short) x; 
}

In order to define a short like this:

auto PositiveShort =  42_s;
auto NegativeShort = -42_s;

However, as explained in this post the C++11 Standard forbids the above implementation of the user-defined literal:

Per paragraph 13.5.8./3 of the C++11 Standard on user-defined literals: The declaration of a literal operator shall have a parameter-declaration-clause equivalent to one of the following:

const char*
unsigned long long int
long double
char
wchar_t
char16_t
char32_t
const char*, std::size_t
const wchar_t*, std::size_t
const char16_t*, std::size_t
const char32_t*, std::size_t

For the positive case I could just use a unsigned long long int but this will not work for the negative case. Is there a workaround maybe using newer futures of c++?

BlueTune
  • 1,023
  • 6
  • 18

1 Answers1

4

As explained here, the unary - is applied to the result of 42_s, so it seems that integral promotion cannot be avoided. Depending on applications, the following workaround might be of some use:

struct Short {    
    short v;

    short operator+() const {
        return v;
    }

    short operator-() const {
        return -v;
    }
};

Short operator"" _s(unsigned long long x) { 
    return Short{static_cast<short>(x)};
}

auto PositiveShort = +42_s;
auto NegativeShort = -42_s;

static_assert(std::is_same_v<decltype(PositiveShort), short>);
static_assert(std::is_same_v<decltype(NegativeShort), short>);
Evg
  • 25,259
  • 5
  • 41
  • 83