文字charT数组

时间:2016-01-20 14:24:48

标签: c++ templates c++11 string-literals

我正在处理涉及文本的算法的某些API。

我想使它不依赖于字符类型(charwchar_t ...),所以我使用模板参数CharT制作了模板类。 这些类使用std::basic_string<CharT>

我必须用默认值初始化很多basic_string。 如果CharTchar我可以影响文字&#34; default_text&#34;,或者如果CharT是wchar_t我可以影响L&#34; default_text&#34;,但这是不是通用的(它是CharT依赖的)。

您是否考虑过使用泛型方法初始化basic_string的方法?

如果这可能会有所帮助,我的代码就在C++11

1 个答案:

答案 0 :(得分:2)

由于您的代码是通用的,我猜您的文字只包含ASCII字符。否则,你必须动态转码,这将是一个很麻烦的事情。为了将类型为char[]的纯ASCII字符串文字提升为另一种字符类型,您可以单独提升每个字符。

如果您要初始化std::basic_string,您也可以立即执行此操作。以下函数采用char[]字符串文字和目标类型,并将其提升为该类型的字符串。

template <typename CharT>
auto
as_string(const char *const text)
{
  const auto length = std::strlen(text);
  auto string = std::basic_string<CharT> {};
  string.resize(length);
  for (auto i = std::size_t {}; i < length; ++i)
    string[i] = CharT {text[i]};
  return string;
}

可以像这样使用。

std::cout << as_string<char>("The bats are in the belfry") << '\n';
std::wcout << as_string<wchar_t>("The dew is on the moor") << L'\n';

但你要求的是一个字符数组,而不是std::basic_string。在C ++ 14中,constexpr可以为此提供很多帮助。请注意,您需要最新的编译器才能得到支持。

我们要做的第一件事就是滚动我们提供std::array操作的constexpr版本。你可以随心所欲,但我会在这里保持简单。

template <typename T, std::size_t N>
struct array { T data[N]; };

接下来,我们还需要constexprstd::strlen

template <typename CharT>
constexpr auto
cstrlen(const CharT *const text) noexcept
{
  auto length = std::size_t {};
  for (auto s = text; *s != CharT {0}; ++s)
    ++length;
  return length;
}

现在我们可以编写一个constexpr函数来提升字符串文字。

template <typename CharT, std::size_t Length>
constexpr auto
as_array(const char *const text)
{
  auto characters = array<CharT, Length + 1> {};
  if (cstrlen(text) != Length)
    throw std::invalid_argument {"Don't lie about the length!"};
  for (auto i = std::size_t {}; i < Length; ++i)
    characters.data[i] = text[i];
  characters.data[Length] = CharT {0};
  return characters;
}

将它包装到宏中可能很方便。对不起,我很抱歉。

#define AS_ARRAY(Type, Text) as_array<Type, cstrlen(Text)>(Text).data

可以像这样使用。

std::cout << AS_ARRAY(char, "The bats are in the belfry") << '\n';
std::wcout << AS_ARRAY(wchar_t, "The dew is on the moor") << L'\n';