<commit_before>---
layout: post
title: ライブコールから自動で曲は作れるのか
---

本記事はNCC Advent Calendar 2015の8日目の記事です。昨日は [@3846masa](https://twitter.com/3846masa) 先輩で、[Raspberry Pi Zero が 届いた話](http://3846masa.hatenablog.jp/entry/2015/12/07/235225) でした。

## Meleteとは

![](https://i.gyazo.com/5f1593ee784fca5a1bc0376b0300295e.png)

Meleteとは、日本語歌詞から自動で作曲する[Orpheus](http://www.orpheus-music.org/v3/Orpheus-top.php)の論文やインターフェイスを参考にほぼ完全なクローンを目指すシステムです。これに至った経緯としては、以下の様なものが挙げられます。

- 昨年度配属していた研究室がまさにOrpheusを作っている研究室であった
- Orpheusのソースコードは肥大化しており、自分には手に負えない状態であった
- Orpheusのソースコードは公開されておらず、自動作曲の発展性を妨げている
- ゼミの課題だった

雑談ですが、Orpheusはギリシャ神話の登場人物から名付けられたということで、Meleteの名前もムーサの3柱の1人である「メレテー」から付けています。システムの読み方は現代風に「**メリート**」と読んでいます。神話の中からプロダクト名を付けるのはダサいと思っているので2度とやらないと思いますが、9人の歌の女神のグループ名[^1]もムーサから名付けられたのと、Meleteという名前が可愛かったので。。

Webアプリケーションとしての開発自体は去年の今頃より行っていますが、Web UIの作成に疲弊しているためなかなか完成しません。<s>なんで世の中にはオープンなピアノロールエディタのコンポーネントや歌声合成APIが無いのだろう。</s>

<iframe src="http://hatenablog-parts.com/embed?url=https://github.com/kvvzr/Melete" width="520px" frameborder="0"></iframe>

今すぐ試したい！という方にはDocker版をオススメします。(TwitterのAPI Keyとか入力しなければいけないので少し面倒かもしれません。ログイン無しで試せる版のPull Requestお待ちしております)

<iframe src="http://hatenablog-parts.com/embed?url=https://hub.docker.com/r/kwzr/docker-melete/" width="520px" frameborder="0"></iframe>

このままでは、永遠に完成しないのでは...?と思ったので自動作曲部分のみ抜き出したコアを先日公開しました。歌詞の形態素解析部分などがPython2.x状態なのでそのうちPython3に対応してPyPIで公開する予定です。

<iframe src="http://hatenablog-parts.com/embed?url=https://github.com/kvvzr/melete-core" width="520px" frameborder="0"></iframe>


### 技術概要
古典的な動的計画法を使った自動作曲法です。**リズム木構造仮説**[^2]や日本語の**イントネーションの高低をメロディに当てはめる**という点が差分であると認識していますが、リズム木構造仮説は出来上がる曲の可能性を狭めていると考え、Meleteでは採用していません。OrpheusやMeleteが自動で作るのはメロディを作る部分だけです。ユーザは歌詞とあらかじめデータベースにあるメロディのリズムパターンやコード進行、音域やBPMなどのパラメータを入力する必要があります。
melete-coreはメロディの自動作曲などの基本的な部分の実装は出来ているのですが、Orpheusには歌声合成機能(これは自前で実装しています)などがあって、まだまだクローンには程遠いなあと思います。

### メロディ生成の流れ

- ユーザが入力した歌詞をアクセント辞書のあるUniDicなどで形態素解析して、「徳井青空」→「と↑くい/あ↑おぞ↓ら」のようにする[^3]
- 1モーラ = 1音符として形態素解析した歌詞とリズムパターンを組み合わせる
- コード進行の構成音の中から歌詞の高低に合う一番高い確率のパスをメロディとします(日本語むずい...
- (Orpheusでは音楽理論においていくつか禁じられているものは生成しないようにしているようです)

![](https://i.gyazo.com/95be850203cc181460e0ab8d8dea0bb0.png)

## ライブコールからの自動作曲
自動作曲システムはパラメータが多いのが難点です(特に様々な曲が作れるようなシステムの場合)。自動作曲システムを使うユーザに音楽の知識を求めるのはおかしい話です。そこでアイドルライブなどのコールからいくつかのパラメータが決められたら楽になるのではないか、と考えたわけです。決してコールから曲を作れたら永遠に騒ぎまくれるという不純な動機ではありません！！[^4]
ライブコールにはいくつか種類がありますが、PPPHのある曲の自動生成を目指したいと思います。

### PPPHとは
ライブコールにはいくつか方言があるので、これという決まりはないようですが、「タン、タタン」というリズムに合わせてクラップをしたり、声を上げたりします。アニメ系のライブでは「オー(ウォー)、ハイ」の繰り返しが一般的だと思います。(オーイングとも言うらしいけどよく分からない...。)また、PPPHの直前にに「(せーの)はーい×2、はい×4」という警報と呼ばれるものを入れたりします。ニコニコ大百科が詳しいです。

<iframe src="http://hatenablog-parts.com/embed?url=http://dic.nicovideo.jp/a/ppph" width="520px" frameborder="0"></iframe>

PPPHを選んだ理由としては、リズムが特徴的であること、警報が節以外の部分に影響する面白いと思ったためです。

### 実装

こんなシステムを作っていますが、作曲経験などが無いので、経験者の方にアドバイスを頂きました。

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr">DTMとかやってる人に聞きたいんだけど、PPPHみたいなコールを入れたいと思って作曲するときってどういう手順を踏みますか</p>&mdash; ぺんぺん@3日目東ム51b (@kwzr) <a href="https://twitter.com/kwzr/status/672103101667520513">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr">普通のオーソドックスな4拍子で16小節1フレーズの曲にすればいいのではないでしょうか</p>&mdash; SSR:【俺の胃袋は宇宙だ】たおまつ (@matsuo_vossler) <a href="https://twitter.com/matsuo_vossler/status/672103451250135040">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr"><a href="https://twitter.com/kwzr">@kwzr</a> PPPHみたいなコールが入りそうなメロディを考える</p>&mdash; いるかアイス (@irucaice) <a href="https://twitter.com/irucaice/status/672104972465471488">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr"><a href="https://twitter.com/kwzr">@kwzr</a> PPPHって基本ポップスにおけるBメロだけど、Aメロサビなどではキックが&#10;ドゥッドゥッドゥッドゥッ&#10;なのに対してBメロで&#10;ドゥッ ドゥッ&#10;ってなったりするとか？</p>&mdash; いるかアイス (@irucaice) <a href="https://twitter.com/irucaice/status/672106136523304960">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

とてもありがたい🙏(特にいるかアイスPにはお世話になりました)
「PPPHみたいなコールが入りそうなメロディ」ですが、メロディだけ聞いてPPPHが入ると分かるものがあるのか検証できそうにないので、今回は考えないことにします。確かにありそうですが。方針としては全体を4拍子にして、Aメロよりゆったりとした伴奏でBメロを作る、いい感じのコード進行でBメロを始める(サブドミナントとか)というのが良さそうだと判断しました。

```python
import melete.lyrics as Lyrics
import melete.rhythm as Rhythm
import melete.chord as Chord
import melete.melody as Melody

# 4/4拍子
ts = Rhythm.TimeSignature(4, 2)

# リズムパターン
rhythms = [[0], [0, 96], [48, 96, 144], [0, 48, 96, 144], [0, 24, 48, 96, 144]]
tree = Rhythm.RhythmTree(48, 1, ts, rhythms)

# 歌詞とリズムを合体
text = u'八ツ橋 を 粉状 に なる まで すりつぶ す===粉状 に したもの に ねっと うを 加え混ぜ る'
lyrics = Lyrics.analyze(text) #歌詞の形態素とイントネーションを調べる
lyrics = map(lambda l: Lyrics.divide(l['phoneme'], tree), lyrics)
beats = map(lambda l: Lyrics.pair(l, tree), lyrics)

# コード進行
c = Chord.Chord.from_name('C')
f = Chord.Chord.from_name('F')
f.inversion(1)
g = Chord.Chord.from_name('G')
g.inversion(1)
progs = [
    Chord.ChordProg(48, 4, [(c, 0), (g, 192), (f, 384), (c, 576)]),
    Chord.ChordProg(48, 4, [(f, 0), (c, 192), (g, 384), (c, 576)])
]

# 伴奏のパターン(最近作ったのでcore側が適当)
accom_patterns = [
    {
        0.0: {'length': 0.25, 'notes': [1, 2]},
        0.25: {'length': 0.25, 'notes': [0]},
        0.5: {'length': 0.25, 'notes': [1, 2]},
        0.75: {'length': 0.25, 'notes': [0]},
    },
    {
        0.0: {'length': 1.0, 'notes': [0, 1, 2]},
    }
]

note_range = Chord.note_range('C4', 'A5')

midi = Melody.create(ts, beats, progs, note_range, accom_patterns, bpm=240)

...
```<commit_msg>コードが表示されないので更新<commit_after>---
layout: post
title: ライブコールから自動で曲は作れるのか
---

本記事はNCC Advent Calendar 2015の8日目の記事です。昨日は [@3846masa](https://twitter.com/3846masa) 先輩で、[Raspberry Pi Zero が 届いた話](http://3846masa.hatenablog.jp/entry/2015/12/07/235225) でした。

## Meleteとは

![](https://i.gyazo.com/5f1593ee784fca5a1bc0376b0300295e.png)

Meleteとは、日本語歌詞から自動で作曲する[Orpheus](http://www.orpheus-music.org/v3/Orpheus-top.php)の論文やインターフェイスを参考にほぼ完全なクローンを目指すシステムです。これに至った経緯としては、以下の様なものが挙げられます。

- 昨年度配属していた研究室がまさにOrpheusを作っている研究室であった
- Orpheusのソースコードは肥大化しており、自分には手に負えない状態であった
- Orpheusのソースコードは公開されておらず、自動作曲の発展性を妨げている
- ゼミの課題だった

雑談ですが、Orpheusはギリシャ神話の登場人物から名付けられたということで、Meleteの名前もムーサの3柱の1人である「メレテー」から付けています。システムの読み方は現代風に「**メリート**」と読んでいます。神話の中からプロダクト名を付けるのはダサいと思っているので2度とやらないと思いますが、9人の歌の女神のグループ名[^1]もムーサから名付けられたのと、Meleteという名前が可愛かったので。。

Webアプリケーションとしての開発自体は去年の今頃より行っていますが、Web UIの作成に疲弊しているためなかなか完成しません。<s>なんで世の中にはオープンなピアノロールエディタのコンポーネントや歌声合成APIが無いのだろう。</s>

<iframe src="http://hatenablog-parts.com/embed?url=https://github.com/kvvzr/Melete" width="520px" frameborder="0"></iframe>

今すぐ試したい！という方にはDocker版をオススメします。(TwitterのAPI Keyとか入力しなければいけないので少し面倒かもしれません。ログイン無しで試せる版のPull Requestお待ちしております)

<iframe src="http://hatenablog-parts.com/embed?url=https://hub.docker.com/r/kwzr/docker-melete/" width="520px" frameborder="0"></iframe>

このままでは、永遠に完成しないのでは...?と思ったので自動作曲部分のみ抜き出したコアを先日公開しました。歌詞の形態素解析部分などがPython2.x状態なのでそのうちPython3に対応してPyPIで公開する予定です。

<iframe src="http://hatenablog-parts.com/embed?url=https://github.com/kvvzr/melete-core" width="520px" frameborder="0"></iframe>


### 技術概要
古典的な動的計画法を使った自動作曲法です。**リズム木構造仮説**[^2]や日本語の**イントネーションの高低をメロディに当てはめる**という点が差分であると認識していますが、リズム木構造仮説は出来上がる曲の可能性を狭めていると考え、Meleteでは採用していません。OrpheusやMeleteが自動で作るのはメロディを作る部分だけです。ユーザは歌詞とあらかじめデータベースにあるメロディのリズムパターンやコード進行、音域やBPMなどのパラメータを入力する必要があります。
melete-coreはメロディの自動作曲などの基本的な部分の実装は出来ているのですが、Orpheusには歌声合成機能(これは自前で実装しています)などがあって、まだまだクローンには程遠いなあと思います。

### メロディ生成の流れ

- ユーザが入力した歌詞をアクセント辞書のあるUniDicなどで形態素解析して、「徳井青空」→「と↑くい/あ↑おぞ↓ら」のようにする[^3]
- 1モーラ = 1音符として形態素解析した歌詞とリズムパターンを組み合わせる
- コード進行の構成音の中から歌詞の高低に合う一番高い確率のパスをメロディとします(日本語むずい...
- (Orpheusでは音楽理論においていくつか禁じられているものは生成しないようにしているようです)

![](https://i.gyazo.com/95be850203cc181460e0ab8d8dea0bb0.png)

## ライブコールからの自動作曲
自動作曲システムはパラメータが多いのが難点です(特に様々な曲が作れるようなシステムの場合)。自動作曲システムを使うユーザに音楽の知識を求めるのはおかしい話です。そこでアイドルライブなどのコールからいくつかのパラメータが決められたら楽になるのではないか、と考えたわけです。決してコールから曲を作れたら永遠に騒ぎまくれるという不純な動機ではありません！！[^4]
ライブコールにはいくつか種類がありますが、PPPHのある曲の自動生成を目指したいと思います。

### PPPHとは
ライブコールにはいくつか方言があるので、これという決まりはないようですが、「タン、タタン」というリズムに合わせてクラップをしたり、声を上げたりします。アニメ系のライブでは「オー(ウォー)、ハイ」の繰り返しが一般的だと思います。(オーイングとも言うらしいけどよく分からない...。)また、PPPHの直前にに「(せーの)はーい×2、はい×4」という警報と呼ばれるものを入れたりします。ニコニコ大百科が詳しいです。

<iframe src="http://hatenablog-parts.com/embed?url=http://dic.nicovideo.jp/a/ppph" width="520px" frameborder="0"></iframe>

PPPHを選んだ理由としては、リズムが特徴的であること、警報が節以外の部分に影響する面白いと思ったためです。

### 実装

こんなシステムを作っていますが、作曲経験などが無いので、経験者の方にアドバイスを頂きました。

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr">DTMとかやってる人に聞きたいんだけど、PPPHみたいなコールを入れたいと思って作曲するときってどういう手順を踏みますか</p>&mdash; ぺんぺん@3日目東ム51b (@kwzr) <a href="https://twitter.com/kwzr/status/672103101667520513">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr">普通のオーソドックスな4拍子で16小節1フレーズの曲にすればいいのではないでしょうか</p>&mdash; SSR:【俺の胃袋は宇宙だ】たおまつ (@matsuo_vossler) <a href="https://twitter.com/matsuo_vossler/status/672103451250135040">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr"><a href="https://twitter.com/kwzr">@kwzr</a> PPPHみたいなコールが入りそうなメロディを考える</p>&mdash; いるかアイス (@irucaice) <a href="https://twitter.com/irucaice/status/672104972465471488">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr"><a href="https://twitter.com/kwzr">@kwzr</a> PPPHって基本ポップスにおけるBメロだけど、Aメロサビなどではキックが&#10;ドゥッドゥッドゥッドゥッ&#10;なのに対してBメロで&#10;ドゥッ ドゥッ&#10;ってなったりするとか？</p>&mdash; いるかアイス (@irucaice) <a href="https://twitter.com/irucaice/status/672106136523304960">2015, 12月 2</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

とてもありがたい🙏(特にいるかアイスPにはお世話になりました)
「PPPHみたいなコールが入りそうなメロディ」ですが、メロディだけ聞いてPPPHが入ると分かるものがあるのか検証できそうにないので、今回は考えないことにします。確かにありそうですが。方針としては全体を4拍子にして、Aメロよりゆったりとした伴奏でBメロを作る、いい感じのコード進行でBメロを始める(サブドミナントとか)というのが良さそうだと判断しました。

<script src="https://gist.github.com/kvvzr/b716fdc0042e5f5fe796.js"></script>
{'fraction_non_alphanumeric': 0.15561959654178675, 'fraction_numerical': 0.053794428434197884, 'mean_word_length': 9.117589893100098, 'pattern_counts': {'":': 0, '<': 97, '<?xml version=': 0, '>': 97, 'https://': 25, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 1, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1044072', 'n_tokens_mistral': 7626, 'n_tokens_neox': 6830, 'n_words': 410}