スポンサーリンク

| キーワード:

C++でsplit (3) – utf16版

1.補助関数の作成

次のutf16文字へのポインタを取得する

char16_t* next_c_u16(const char16_t* c) {
  if (IS_SURROGATE_PAIR(c[0], c[1]) == true)
    return (char16_t*)c + 2;
  return (char16_t*)c + 1;
}

utf16文字を一文字取り出す

//utf16文字を一文字取り出す
void ext_c_u16(char16_t* const dst, const char16_t* src,int* size) {
  int sz;
  if (IS_SURROGATE_PAIR(src[0], src[1]) == true)
    sz = 4;
  else
    sz = 2;

  memcpy(dst, src, sz);
  dst[sz/2] = char16_t(0);

  if(size)
    *size = sz;
}

utf16文字を比較する

//utf16文字を比較する
bool cmp_c_u16(const char16_t* c1, const char16_t* c2) {
  int K = bytes_c_u16(c1);
  int L = bytes_c_u16(c2);

  if (K != L)
    return false;

  bool issame = (memcmp(c1, c2, K) == 0);
  return issame;
}

utf16文字のバイト数を返す関数

//文字のバイト数を取得
int bytes_c_u16(const char16_t* c) {
  if (IS_SURROGATE_PAIR(c[0], c[1]) == true)
    return 4;
  return 2;
}

split関数本体

std::vector<std::u16string> split_u16(const char16_t* src, const char16_t* del) {

  char16_t tmp[10];

  std::vector<std::u16string> result;

  std::u16string tmps;
  while (*src) {

    //デリミタを飛ばす
    const char16_t* p = src;
    while (cmp_c_u16(src, del) == true && *src != '\0')
      src = next_c_u16(src);

    //デリミタに遭遇するまで文字を追加し続ける
    while (cmp_c_u16(src, del) != true && *src != '\0') {
      ext_c_u16(tmp, src, nullptr);//一文字取り出す
      tmps += tmp;
      src = next_c_u16(src);
    }
    if (tmps.size()) {
      result.push_back(tmps);
    }
    tmps.clear();
  }

  return result;
}

実験1

int main()
{

  setlocale(LC_ALL, "");

  char16_t* u16 = (char16_t*)L"C:\\いろは\\山田\\abc\\";

  std::ofstream f(L"c:\\test\\test.txt", std::ios::out | std::ios::binary);

  std::vector<std::u16string> ret = split_u16(u16, (char16_t*)L"\\");

  for (size_t i = 0; i < ret.size(); i++) {
    wprintf(L"[%s]", (wchar_t*)ret[i].c_str());
  }

  f.close();

  return 0;
}

結果1

[C:][いろは][山田][abc]

実験2

結果2

余談

サロゲートペアの文字一覧はここから

サロゲートペア - 闘うITエンジニアの覚え書き

WordPressで上記文字を入力したところなぜか記事の保存ができなかったので、実験2は画像にしている。

C++でsplit (1) – strtok版

C++でsplit (2) – マルチバイト版,’\’対応

C++でsplit (3) – utf16版

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)


この記事のトラックバックURL: