附代码 你想用深度学习谱写自己的音乐吗?这篇指南来帮助你!( 五 )

我们将为输入数据准备整数序列
1. #preparing input sequences2. x_seq=[]3. for i in x:4.temp=[]5.for j in i:6.#assigning unique integer to every note7.temp.append(x_note_to_int[j])8.x_seq.append(temp)9.10. x_seq = np.array(x_seq)同样 , 也为输出数据准备整数序列
1. unique_y = list(set(y))2. y_note_to_int = dict((note_, number) for number, note_ in enumerate(unique_y))3. y_seq=np.array([y_note_to_int[i] for i in y])让我们保留80%的数据用于训练 , 其余20%的用于评估:
1. from sklearn.model_selection import train_test_split2. x_tr, x_val, y_tr, y_val = train_test_split(x_seq,y_seq,test_size=0.2,random_state=0)构建模型
我在这里定义了2种架构– WaveNet和LSTM 。请尝试两种架构 , 以了解WaveNet架构的重要性 。
1. def lstm():2.model = Sequential()3.model.add(LSTM(128,return_sequences=True))4.model.add(LSTM(128))5.model.add(Dense(256))6.model.add(Activation('relu'))7.model.add(Dense(n_vocab))8.model.add(Activation('softmax'))9.model.compile(loss='sparse_categorical_crossentropy', optimizer='adam')10.return model我简化了WaveNet的架构 , 没有添加残差连接和跳跃连接 , 因为这些层的作用是提高收敛速度(WaveNet以原始音频波作为输入) 。但在我们的例子中 , 输入是一组音符和和弦 , 因为我们在生成音乐:
1. from keras.layers import *2. from keras.models import *3. from keras.callbacks import *4. import keras.backend as K5.6. K.clear_session()7. model = Sequential()8.9. #embedding layer10. model.add(Embedding(len(unique_x), 100, input_length=32,trainable=True))11.12. model.add(Conv1D(64,3, padding='causal',activation='relu'))13. model.add(Dropout(0.2))14. model.add(MaxPool1D(2))15.16. model.add(Conv1D(128,3,activation='relu',dilation_rate=2,padding='causal'))17. model.add(Dropout(0.2))18. model.add(MaxPool1D(2))19.20. model.add(Conv1D(256,3,activation='relu',dilation_rate=4,padding='causal'))21. model.add(Dropout(0.2))22. model.add(MaxPool1D(2))23.24. #model.add(Conv1D(256,5,activation='relu'))25. model.add(GlobalMaxPool1D())26.27. model.add(Dense(256, activation='relu'))28. model.add(Dense(len(unique_y), activation='softmax'))29.30. model.compile(loss='sparse_categorical_crossentropy', optimizer='adam')31.32. model.summary()定义回调以在训练期间保存最佳模型:
mc=ModelCheckpoint('best_model.h5', monitor='val_loss', mode='min', save_best_only=True,verbose=1)
让我们使用128的批大小将模型训练50个epoch:
history = model.fit(np.array(x_tr),np.array(y_tr),batch_size=128,epochs=50,validation_data=https://www.isolves.com/it/ai/2020-07-19/(np.array(x_val),np.array(y_val)),verbose=1, callbacks=[mc])
导入最好的模型:
1. #loading best model2. from keras.models import load_model3. model = load_model('best_model.h5')是时候创作我们自己的音乐了 。我们将按照推断阶段中提到的步骤进行预测 。
1. import random2. ind = np.random.randint(0,len(x_val)-1)3.4. random_music = x_val[ind]5.6. predictions=[]7. for i in range(10):8.9.random_music = random_music.reshape(1,no_of_timesteps)10.11.prob= model.predict(random_music)[0]12.y_pred= np.argmax(prob,axis=0)13.predictions.append(y_pred)14.15.random_music = np.insert(random_music[0],len(random_music[0]),y_pred)16.random_music = random_music[1:]17.18. print(predictions)现在 , 我们将整数还原为音符 。
1. x_int_to_note = dict((number, note_) for number, note_ in enumerate(unique_x))2. predicted_notes = [x_int_to_note[i] for i in predictions]  最后一步是将预测结果转换回MIDI文件 。让我们定义一个函数来完成此任务 。
1. def convert_to_midi(prediction_output):2.3.offset = 04.output_notes = []5.6.# create note and chord objects based on the values generated by the model7.for pattern in prediction_output:8.9.# pattern is a chord10.if ('.' in pattern) or pattern.isdigit():11.notes_in_chord = pattern.split('.')12.notes = []13.for current_note in notes_in_chord:14.15.cn=int(current_note)16.new_note = note.Note(cn)17.new_note.storedInstrument = instrument.Piano()18.notes.append(new_note)19.20.new_chord = chord.Chord(notes)21.new_chord.offset = offset22.output_notes.append(new_chord)23.24.# pattern is a note25.else:26.27.new_note = note.Note(pattern)28.new_note.offset = offset29.new_note.storedInstrument = instrument.Piano()30.output_notes.append(new_note)31.32.# increase offset each iteration so that notes do not stack33.offset += 134.midi_stream = stream.Stream(output_notes)35.midi_stream.write('midi', fp='music.mid')


推荐阅读