在C++11中从用户定义的字面量返回一个std::array

6

我刚刚安装了gcc-4.8.1并且发现可以使用-std=c++1y来获取多行的constexpr,我感到非常兴奋。但是我很好奇是否有任何方法使它能够工作呢?

#include <array>

constexpr auto operator "" _a1 (const char* text, const size_t size) -> std::array<char,size> {
    std::array<char,size>() blah;
    std::strncpy(blah.data(), test, size);

    // do some stuff to blah at compile time

    return blah;
}


int main() {
    auto blah = "hello world"_a2;
}

但我遇到了一个非常糟糕的问题:
$ g++ test.cpp -std=gnu++1y -Wall -Werror -Wextra -Weffc++ -pedantic
test.cpp:3:100: error: use of parameter ‘size’ outside function body
 constexpr auto operator "" _a1 (const char* text, const size_t size) -> std::array<char,size> {
                                                                                                    ^
test.cpp:3:100: error: use of parameter ‘size’ outside function body
test.cpp:3:100: error: use of parameter ‘size’ outside function body
test.cpp:3:104: error: template argument 2 is invalid
 constexpr auto operator "" _a1 (const char* text, const size_t size) -> std::array<char,size> {
                                                                                                        ^
test.cpp: In function ‘int main()’:
test.cpp:26:17: error: unable to find string literal operator ‘operator"" _a1’
     auto blah = "hello world"_a1;

有没有办法实现这个功能?我无法从constexpr返回std :: string,并且似乎没有任何模板或decltype可以使用。有没有办法从参数中获取常量表达式?

1个回答

7

您需要一个模板字面量运算符。函数参数从未是有效的常量表达式; 即使正常使用有意义,您的运算符仍必须支持形式为的显式调用

operator "" _a1 ( "hello", 5 );

对于整数和浮点数的用户自定义字面量,有一个模板形式可以返回一个array

template< char ... c >
constexpr std::array< char, sizeof ... (c) >
operator "" _a1 () {
    return { c ... };
}

这种方法目前似乎不支持字符串字面量,可能与多字节编码的问题有关。

所以,在这种特定的方法中,你运气不太好。

不过,你可以采取另一种方法,将字符串视为数组。

template< std::size_t size >
constexpr std::array< char, size >
string_to_array( char const (&str)[ size ] )
    { return string_to_array( str, make_index_helper< size >() ); }

template< std::size_t size, std::size_t ... index >
constexpr std::array< char, size >
string_to_array( char const (&str)[ size ],
                 index_helper< index ... > )
    { return {{ str[ index ] ... }}; }

这需要一个支持模板index_helper来生成一组整数计数包,例如{0,1,2,... size}
另外请注意,constexpr可能不适用于您所想要的应用程序。 constexpr函数不能包含一系列命令式语句。唯一允许计算任何东西的语句是return,或者对于constexpr构造函数,是成员初始化。
更新:这里有一个小演示,可以在C++11中完成。 (链接)

看起来很酷,我今天下午会试一试。C++14将支持多行constexpr函数,但看起来我错了,这还没有被gcc实现。 - HNJSlater

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接