LoginSignup
4
1

More than 3 years have passed since last update.

楽譜をランダム生成するコード

Last updated at Posted at 2020-04-02

楽譜をランダムで生成するコードを作りました。機械学習の楽譜のデータセット作成用として使ってください。

こんな感じの画像ができます

0.png

1.png

2.png

3.png

環境

  • chromebookのdebian9 (stretch)
  • numpy (1.16.6)
  • music21 (5.7.2)
  • lilypond (2.18.2)
  • python3 (3.5.3)

必要なライブラリーやソフト

pythonのライブラリー:

  • numpy
  • music21

ソフト:

  • lilypond

コード

randomScore.py
import music21 as m21
from numpy.random import choice

def makeScore(symbleNum=200, scoreNum=20, noteRange=[3, 4, 5, 6, 7],
              noteRangeProbs=[0.05, 0.4, 0.4, 0.1, 0.05], sharpProb=0.1, 
              restProb=0.2, exportDir='/home'):

    '''
    symbleNum:楽譜一枚あたり何個の音符と休符があるか
    scoreNum:楽譜を何枚生成するか
    noteRange:何オクターブ目から何オクターブ目の音符があるか(デフォルトはC3からB#7まで)
    noteRangeProbs:それぞれの音符がオクターブ別にどのくらい出てくるかの確率のリスト
    sharpProb:音符にシャープがつく確率
    restProb:休符が出る確率
    exportDir:出力ファイルの保存先
    ===========================
    デフォルトではファイル名は1, 2, 3, ... となっております。
    .pngファイルの他に色々なファイルが出ますが、消していいです。
    '''

    quarterLengths = [4, 2.5, 2, 1.5, 1, 0.75, 0.5, 0.25]
    notes = ['C', 'D', 'E', 'F', 'G', 'A', 'B']
    noteRange = list(map(lambda x: str(x), noteRange))
    typeProbs = [1 - restProb, restProb]
    sharpProbs = [sharpProb, 1 - sharpProb]
    chooseThese = [True, False]

    for i in range(scoreNum):
        noteList = []
        measure = m21.stream.Measure()

        for j in range(symbleNum):
            if choice(a=chooseThese, p=typeProbs):
                if choice(a=chooseThese, p=sharpProbs):
                    pitchName = choice(notes) + '#' + choice(a=noteRange, p=noteRangeProbs)

                else:
                    pitchName = choice(notes) + choice(a=noteRange, p=noteRangeProbs)

                n = m21.note.Note(pitchName, quarterLength=choice(quarterLengths))
                noteList.append(n)

            else:
                n = m21.note.Rest(quarterLength = choice(quarterLengths))
                noteList.append(n)

        measure.append(noteList)
        fileName = exportDir + str(i)
        measure.write('lily.png', fileName)

if __name__ == "__main__":
    makeScore()

悪いところ

  • 四拍子だけ
  • 一小節内の音符の数がおかしい
  • 音楽的に(旋律)おかしい
  • フラットがない
  • 題名がない
  • ダイナミクス、アーティキュレーションがない

などなど

4
1
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
1