Rubyで平仮名(ひらがな)と片仮名(カタカナ)に濁点と半濁点を付ける

## 方法

平仮名と片仮名に濁点・半濁点の結合文字を付加する。

濁点の結合文字は U+3099
半濁点の結合文字は U+309A

[結合文字 \- Wikipedia](https://ja.wikipedia.org/wiki/%E7%B5%90%E5%90%88%E6%96%87%E5%AD%97)

> 結合文字（けつごうもじ、英語: combining character）とは、文字コードにおいて先行する文字と組み合わせるための図形文字をいう。ダイアクリティカルマークや、仮名の結合可能な濁点・半濁点、ヘブライ文字のニクダー、アラビア文字のシャクル、ブラーフミー系文字の母音記号などが結合文字に属する。異体字セレクタも結合文字の一種である。

これを利用すると、一般的に濁音・半濁音にならない「あ」のような文字にも濁点・半濁点を付けることができる。

(Macのターミナルに表示した例)
![agyo.png](https://qiita-image-store.s3.amazonaws.com/0/139365/4c7f928b-be0a-8364-13ae-79b0e6ef12c4.png)

また、「ば」「ぱ」のように合成済み文字に濁点・半濁点を付けることもできるようだが……

(Macのターミナルに表示した例)
![hagyo.png](https://qiita-image-store.s3.amazonaws.com/0/139365/67dfb3f3-9871-4fd7-26f5-d4b1cb684321.png)

## 平仮名(ひらがな)の「あ」から「ん」に濁点・半濁点を付ける

### ソースコード

```ruby
# 文字のコードポイントを取得
a = 'あ'.codepoints[0]
n = 'ん'.codepoints[0]

# 「あ」から「ん」まで出力
(a..n).each do |c|
  # コードポイントを文字へ変換
  moji = c.chr(Encoding::UTF_8) 
  # コードポイント(10進数)
  cp10 = c.to_s
  # コードポイント(16進数)
  cp16 = c.to_s(16)
  # 濁点を付ける
  dkon = moji + "\u3099"
  # 半濁点を付ける
  hndk = moji + "\u309a"
  # 濁点と半濁点を付ける
  dkhd = moji + "\u3099\u309a"
  # 出力
  puts "#{moji} #{cp10} #{cp16} #{dkon} #{hndk} #{dkhd}"
end
```

### 出力結果

```
あ 12354 3042 あ゙ あ゚ あ゙゚
ぃ 12355 3043 ぃ゙ ぃ゚ ぃ゙゚
い 12356 3044 い゙ い゚ い゙゚
ぅ 12357 3045 ぅ゙ ぅ゚ ぅ゙゚
う 12358 3046 ゔ う゚ ゔ゚
ぇ 12359 3047 ぇ゙ ぇ゚ ぇ゙゚
え 12360 3048 え゙ え゚ え゙゚
ぉ 12361 3049 ぉ゙ ぉ゚ ぉ゙゚
お 12362 304a お゙ お゚ お゙゚
か 12363 304b が か゚ が゚
が 12364 304c が゙ が゚ が゙゚
き 12365 304d ぎ き゚ ぎ゚
ぎ 12366 304e ぎ゙ ぎ゚ ぎ゙゚
く 12367 304f ぐ く゚ ぐ゚
ぐ 12368 3050 ぐ゙ ぐ゚ ぐ゙゚
け 12369 3051 げ け゚ げ゚
げ 12370 3052 げ゙ げ゚ げ゙゚
こ 12371 3053 ご こ゚ ご゚
ご 12372 3054 ご゙ ご゚ ご゙゚
さ 12373 3055 ざ さ゚ ざ゚
ざ 12374 3056 ざ゙ ざ゚ ざ゙゚
し 12375 3057 じ し゚ じ゚
じ 12376 3058 じ゙ じ゚ じ゙゚
す 12377 3059 ず す゚ ず゚
ず 12378 305a ず゙ ず゚ ず゙゚
せ 12379 305b ぜ せ゚ ぜ゚
ぜ 12380 305c ぜ゙ ぜ゚ ぜ゙゚
そ 12381 305d ぞ そ゚ ぞ゚
ぞ 12382 305e ぞ゙ ぞ゚ ぞ゙゚
た 12383 305f だ た゚ だ゚
だ 12384 3060 だ゙ だ゚ だ゙゚
ち 12385 3061 ぢ ち゚ ぢ゚
ぢ 12386 3062 ぢ゙ ぢ゚ ぢ゙゚
っ 12387 3063 っ゙ っ゚ っ゙゚
つ 12388 3064 づ つ゚ づ゚
づ 12389 3065 づ゙ づ゚ づ゙゚
て 12390 3066 で て゚ で゚
で 12391 3067 で゙ で゚ で゙゚
と 12392 3068 ど と゚ ど゚
ど 12393 3069 ど゙ ど゚ ど゙゚
な 12394 306a な゙ な゚ な゙゚
に 12395 306b に゙ に゚ に゙゚
ぬ 12396 306c ぬ゙ ぬ゚ ぬ゙゚
ね 12397 306d ね゙ ね゚ ね゙゚
の 12398 306e の゙ の゚ の゙゚
は 12399 306f ば ぱ ば゚
ば 12400 3070 ば゙ ば゚ ば゙゚
ぱ 12401 3071 ぱ゙ ぱ゚ ぱ゙゚
ひ 12402 3072 び ぴ び゚
び 12403 3073 び゙ び゚ び゙゚
ぴ 12404 3074 ぴ゙ ぴ゚ ぴ゙゚
ふ 12405 3075 ぶ ぷ ぶ゚
ぶ 12406 3076 ぶ゙ ぶ゚ ぶ゙゚
ぷ 12407 3077 ぷ゙ ぷ゚ ぷ゙゚
へ 12408 3078 べ ぺ べ゚
べ 12409 3079 べ゙ べ゚ べ゙゚
ぺ 12410 307a ぺ゙ ぺ゚ ぺ゙゚
ほ 12411 307b ぼ ぽ ぼ゚
ぼ 12412 307c ぼ゙ ぼ゚ ぼ゙゚
ぽ 12413 307d ぽ゙ ぽ゚ ぽ゙゚
ま 12414 307e ま゙ ま゚ ま゙゚
み 12415 307f み゙ み゚ み゙゚
む 12416 3080 む゙ む゚ む゙゚
め 12417 3081 め゙ め゚ め゙゚
も 12418 3082 も゙ も゚ も゙゚
ゃ 12419 3083 ゃ゙ ゃ゚ ゃ゙゚
や 12420 3084 や゙ や゚ や゙゚
ゅ 12421 3085 ゅ゙ ゅ゚ ゅ゙゚
ゆ 12422 3086 ゆ゙ ゆ゚ ゆ゙゚
ょ 12423 3087 ょ゙ ょ゚ ょ゙゚
よ 12424 3088 よ゙ よ゚ よ゙゚
ら 12425 3089 ら゙ ら゚ ら゙゚
り 12426 308a り゙ り゚ り゙゚
る 12427 308b る゙ る゚ る゙゚
れ 12428 308c れ゙ れ゚ れ゙゚
ろ 12429 308d ろ゙ ろ゚ ろ゙゚
ゎ 12430 308e ゎ゙ ゎ゚ ゎ゙゚
わ 12431 308f わ゙ わ゚ わ゙゚
ゐ 12432 3090 ゐ゙ ゐ゚ ゐ゙゚
ゑ 12433 3091 ゑ゙ ゑ゚ ゑ゙゚
を 12434 3092 を゙ を゚ を゙゚
ん 12435 3093 ん゙ ん゚ ん゙゚
```

## 片仮名(カタカナ)の「ア」から「ン」に濁点・半濁点を付ける

## ソースコード

```ruby
# 文字のコードポイントを取得
a = 'ア'.codepoints[0]
n = 'ン'.codepoints[0]

# 「ア」から「ン」まで出力
(a..n).each do |c|
  # コードポイントを文字へ変換
  moji = c.chr(Encoding::UTF_8) 
  # コードポイント(10進数)
  cp10 = c.to_s
  # コードポイント(16進数)
  cp16 = c.to_s(16)
  # 濁点を付ける
  dkon = moji + "\u3099"
  # 半濁点を付ける
  hndk = moji + "\u309a"
  # 濁点と半濁点を付ける
  dkhd = moji + "\u3099\u309a"
  # 出力
  puts "#{moji} #{cp10} #{cp16} #{dkon} #{hndk} #{dkhd}"
end
```

### 出力結果

```
ア 12450 30a2 ア゙ ア゚ ア゙゚
ィ 12451 30a3 ィ゙ ィ゚ ィ゙゚
イ 12452 30a4 イ゙ イ゚ イ゙゚
ゥ 12453 30a5 ゥ゙ ゥ゚ ゥ゙゚
ウ 12454 30a6 ヴ ウ゚ ヴ゚
ェ 12455 30a7 ェ゙ ェ゚ ェ゙゚
エ 12456 30a8 エ゙ エ゚ エ゙゚
ォ 12457 30a9 ォ゙ ォ゚ ォ゙゚
オ 12458 30aa オ゙ オ゚ オ゙゚
カ 12459 30ab ガ カ゚ ガ゚
ガ 12460 30ac ガ゙ ガ゚ ガ゙゚
キ 12461 30ad ギ キ゚ ギ゚
ギ 12462 30ae ギ゙ ギ゚ ギ゙゚
ク 12463 30af グ ク゚ グ゚
グ 12464 30b0 グ゙ グ゚ グ゙゚
ケ 12465 30b1 ゲ ケ゚ ゲ゚
ゲ 12466 30b2 ゲ゙ ゲ゚ ゲ゙゚
コ 12467 30b3 ゴ コ゚ ゴ゚
ゴ 12468 30b4 ゴ゙ ゴ゚ ゴ゙゚
サ 12469 30b5 ザ サ゚ ザ゚
ザ 12470 30b6 ザ゙ ザ゚ ザ゙゚
シ 12471 30b7 ジ シ゚ ジ゚
ジ 12472 30b8 ジ゙ ジ゚ ジ゙゚
ス 12473 30b9 ズ ス゚ ズ゚
ズ 12474 30ba ズ゙ ズ゚ ズ゙゚
セ 12475 30bb ゼ セ゚ ゼ゚
ゼ 12476 30bc ゼ゙ ゼ゚ ゼ゙゚
ソ 12477 30bd ゾ ソ゚ ゾ゚
ゾ 12478 30be ゾ゙ ゾ゚ ゾ゙゚
タ 12479 30bf ダ タ゚ ダ゚
ダ 12480 30c0 ダ゙ ダ゚ ダ゙゚
チ 12481 30c1 ヂ チ゚ ヂ゚
ヂ 12482 30c2 ヂ゙ ヂ゚ ヂ゙゚
ッ 12483 30c3 ッ゙ ッ゚ ッ゙゚
ツ 12484 30c4 ヅ ツ゚ ヅ゚
ヅ 12485 30c5 ヅ゙ ヅ゚ ヅ゙゚
テ 12486 30c6 デ テ゚ デ゚
デ 12487 30c7 デ゙ デ゚ デ゙゚
ト 12488 30c8 ド ト゚ ド゚
ド 12489 30c9 ド゙ ド゚ ド゙゚
ナ 12490 30ca ナ゙ ナ゚ ナ゙゚
ニ 12491 30cb ニ゙ ニ゚ ニ゙゚
ヌ 12492 30cc ヌ゙ ヌ゚ ヌ゙゚
ネ 12493 30cd ネ゙ ネ゚ ネ゙゚
ノ 12494 30ce ノ゙ ノ゚ ノ゙゚
ハ 12495 30cf バ パ バ゚
バ 12496 30d0 バ゙ バ゚ バ゙゚
パ 12497 30d1 パ゙ パ゚ パ゙゚
ヒ 12498 30d2 ビ ピ ビ゚
ビ 12499 30d3 ビ゙ ビ゚ ビ゙゚
ピ 12500 30d4 ピ゙ ピ゚ ピ゙゚
フ 12501 30d5 ブ プ ブ゚
ブ 12502 30d6 ブ゙ ブ゚ ブ゙゚
プ 12503 30d7 プ゙ プ゚ プ゙゚
ヘ 12504 30d8 ベ ペ ベ゚
ベ 12505 30d9 ベ゙ ベ゚ ベ゙゚
ペ 12506 30da ペ゙ ペ゚ ペ゙゚
ホ 12507 30db ボ ポ ボ゚
ボ 12508 30dc ボ゙ ボ゚ ボ゙゚
ポ 12509 30dd ポ゙ ポ゚ ポ゙゚
マ 12510 30de マ゙ マ゚ マ゙゚
ミ 12511 30df ミ゙ ミ゚ ミ゙゚
ム 12512 30e0 ム゙ ム゚ ム゙゚
メ 12513 30e1 メ゙ メ゚ メ゙゚
モ 12514 30e2 モ゙ モ゚ モ゙゚
ャ 12515 30e3 ャ゙ ャ゚ ャ゙゚
ヤ 12516 30e4 ヤ゙ ヤ゚ ヤ゙゚
ュ 12517 30e5 ュ゙ ュ゚ ュ゙゚
ユ 12518 30e6 ユ゙ ユ゚ ユ゙゚
ョ 12519 30e7 ョ゙ ョ゚ ョ゙゚
ヨ 12520 30e8 ヨ゙ ヨ゚ ヨ゙゚
ラ 12521 30e9 ラ゙ ラ゚ ラ゙゚
リ 12522 30ea リ゙ リ゚ リ゙゚
ル 12523 30eb ル゙ ル゚ ル゙゚
レ 12524 30ec レ゙ レ゚ レ゙゚
ロ 12525 30ed ロ゙ ロ゚ ロ゙゚
ヮ 12526 30ee ヮ゙ ヮ゚ ヮ゙゚
ワ 12527 30ef ヷ ワ゚ ヷ゚
ヰ 12528 30f0 ヸ ヰ゚ ヸ゚
ヱ 12529 30f1 ヹ ヱ゚ ヹ゚
ヲ 12530 30f2 ヺ ヲ゚ ヺ゚
ン 12531 30f3 ン゙ ン゚ ン゙゚
```

## 「あ」〜「ん」・「ア」〜「ン」の間に無い文字

「あ」〜「ん」・「ア」〜「ン」の間にすべての平仮名・片仮名が入っているかと思ったら、入っていなかった。
参考までに「あ」〜「ん」・「ア」〜「ン」の間に無い文字について、コードポイントを出力してみる。

## ソースコード

```ruby
# ひらがな
'ゔゕゖ゙゚゛゜ゝゞゟ'.chars.each do |c|
  cp = c.codepoints[0]
  cp10 = cp.to_s
  cp16 = cp.to_s(16)
  puts "#{c} #{cp10} #{cp16}"
end

# カタカナ
'゠ヴヵヶヷヸヹヺ・ーヽヾヿ'.chars.each do |c|
  cp = c.codepoints[0]
  cp10 = cp.to_s
  cp16 = cp.to_s(16)
  puts "#{c} #{cp10} #{cp16}"
end
```

## 出力結果

```
ゔ 12436 3094
ゕ 12437 3095
ゖ 12438 3096
゙ 12441 3099
゚ 12442 309a
゛ 12443 309b
゜ 12444 309c
ゝ 12445 309d
ゞ 12446 309e
ゟ 12447 309f
゠ 12448 30a0
ヴ 12532 30f4
ヵ 12533 30f5
ヶ 12534 30f6
ヷ 12535 30f7
ヸ 12536 30f8
ヹ 12537 30f9
ヺ 12538 30fa
・ 12539 30fb
ー 12540 30fc
ヽ 12541 30fd
ヾ 12542 30fe
ヿ 12543 30ff
```

## 参考資料

- [Unicode一覧 3000\-3FFF \- Wikipedia](https://ja.wikipedia.org/wiki/Unicode%E4%B8%80%E8%A6%A7_3000-3FFF)
- [平仮名 (Unicodeのブロック) - Wikipedia](https://ja.wikipedia.org/wiki/%E5%B9%B3%E4%BB%AE%E5%90%8D_(Unicode%E3%81%AE%E3%83%96%E3%83%AD%E3%83%83%E3%82%AF))
- [片仮名 (Unicodeのブロック) - Wikipedia](https://ja.wikipedia.org/wiki/%E7%89%87%E4%BB%AE%E5%90%8D_(Unicode%E3%81%AE%E3%83%96%E3%83%AD%E3%83%83%E3%82%AF))