Erklären Sie ausführlich, wie Sie mit Python einen Sound erzeugen

Menschen sind Wesen, die selbst synthetische Sprachlesesoftware herstellen möchten. Das ist unvermeidlich. Pascal sagt auch, die Leute denken an Schilf. siehst du? (Was?)

Nun, vorerst werde ich eine Implementierung ausprobieren, die mit Python Sounds mit Nuancen wie dieser vorläufigen Untersuchung erzeugt.

Kapitel.0 Sprache / Modul

python


import numpy as np
import matplotlib.pyplot as pl
import wave
import struct
import pyaudio

Das Jupyter-Notebook könnte den Klang etwas erleichtern (ich kenne die Details nicht), aber nein.

Kapitel 1. Ich muss den Ton mit einem Ausdruck ausdrücken ...

Weißt du was Sound ist? Schall ist wie eine periodische (?) Änderung der Luftdichte. Kurz gesagt, es ist eine Welle. Apropos Wellen, es ist Sünde, cos. Hurra! Abschließend werden wir dieses Mal eine Sinuswelle mit der folgenden Formel verwenden. sin(2πnt/s) note_hz=n sample_hz=s

python


sec = 1 #1 Sekunde
note_hz = 440 #La Schallfrequenz
sample_hz = 44100 #Abtastfrequenz
t = np.arange(0, sample_hz * sec) #Sichern Sie sich eine Zeitspanne von 1 Sekunde
wv = np.sin(2 * np.pi * note_hz * t/sample_hz)

"t" repräsentiert die Zeit von 1 Sekunde und im obigen Fall ist es eine eindimensionale Anordnung von 44100 Elementen. Die Informationen in der Welt, in der wir leben, sind kontinuierlich (analog), aber leider können PCs nur diskrete (digitale) Daten verarbeiten. Daher wird eine Sekunde in 44100 Teile geteilt und ausgedrückt. サンプリング周波数.jpg (Die Abtastfrequenz von 44100 Hz ist übrigens der Standard für die Abtastfrequenz von CD und etwa doppelt so hoch wie der hörbare Bereich des Menschen. Warum wird sie verdoppelt? Lassen Sie uns mit der Nyquist-Frequenz googeln.)

Der Inhalt des Zeichens ist * 2πnt / s *. t / sample_hz * = t / s * erhöht sich auf * 0,1,2, ..., 44100 * Durch Teilen von * t * durch * s = 44100 *, * 0,1 / 44100 , 2/44100, ..., 440099 / 44100,1 *, was "eine Sekunde ausdrückt, die allmählich zunimmt (jeweils 1/44100)".

Wenn Sie note_hz * = n * ignorieren und np.sin (2 * np.pi * t / sample_hz) betrachten = sin (2πt / s) *, ist * t / s * 0 Da es sich um eine Variable handelt, die von → 1 (statt einer Funktion der Zeit?) Ansteigt, ist ersichtlich, dass * 2πt / s * innerhalb von sin von 0 auf 2π ansteigt. Mit anderen Worten, * sin (2πt / s) * ist eine Funktion, die genau in einer Sekunde um den Einheitskreis läuft (eine Welle, die einmal in einer Sekunde vibriert). ![正弦波.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/528997/b18d66b2-6895-7af3-ff4c-ee4604cd0a61.jpeg) Einmal in 1 Sekunde zu vibrieren bedeutet, dass die Frequenz dieser Welle 1 [Hz = 1 / s] beträgt. Bei Frequenz 1 ist es jedoch nicht zu hören. Hier kommt note_hz` * = n * ins Spiel.

Sie können die Frequenz der Welle frei ändern, indem Sie n einfach mit * 2πt / s * multiplizieren. Wenn beispielsweise * n = 440 * ist, wird * sin (2πnt / s) * zu einer Welle („la“ in Bezug auf Schall), die 440 Mal pro Sekunde vibriert.

Dies vervollständigt den Ausdruck des Tons im Programm. Ich werde das oben eingefügte Programm erneut kopieren.

python


sec = 1 #1 Sekunde
note_hz = 440 #La Schallfrequenz
sample_hz = 44100 #Abtastfrequenz
t = np.arange(0, sample_hz * sec) #Sichern Sie sich eine Zeitspanne von 1 Sekunde
wv = np.sin(2 * np.pi * note_hz * t/sample_hz)

Kapitel 2. Lassen Sie uns den vom Programm ausgedrückten Ton an .wav ausgeben. Lass uns das tun.

Der Fluss von hier ist wie folgt.

  1. Geben Sie den erstellten Sound als WAV-Datei aus.
  2. Binär die Sounddaten mit dem Strukturmodul.
  3. Geben Sie die binärisierten Daten als WAV-Datei mit dem Wave-Modul aus.
  4. Spielen Sie den erstellten Sound im Programm ab. (Irgendein)
  5. Öffnen Sie die erstellte WAV-Datei mit dem Wave-Modul
  6. Spielen Sie mit dem Pyaudio-Modul.
  7. Zeigen Sie die Schallwellenform mit dem Modul matplotlib.pyplot als Diagramm an. (Irgendein)

In Bezug auf 3., wenn Sie sich nicht für die Wellenform interessieren, müssen Sie es überhaupt nicht tun. 2. verwendet ein Modul namens pyaudio, aber die Installation mit der Python 3.7-Serie ist problematisch (wenn Sie installieren möchten, lesen Sie bitte die Referenzseite am Ende dieser Seite), sodass die in 1 erstellte .wav-Datei erstellt wird. Sie können die Datei mit Windows Media Player abspielen.

Jetzt werde ich erklären, wie man als .wav ausgibt.

1. Binarisierung

Es ist binärisiert. Binarisierung bedeutet, Daten in Binärzahlen umzuwandeln. Bei Verwendung des Wave-Moduls scheint es nicht möglich zu sein, in die WAV-Datei zu schreiben, es sei denn, sie ist binärisiert. Vielleicht. Machen wir es also binär!

Fügen wir zuerst die Antwort ein.

python


max_num = 32767.0 / max(wv) #Vorbereitung für die Binärisierung
wv16 = [int(x * max_num) for x in wv] #Vorbereitung für die Binärisierung
bi_wv = struct.pack("h" * len(wv16), *wv16) #Binär

Es ist so. (Es ist eher so, als würde man die Site kopieren, auf die ich mich bezog, aber gibt es eine Möglichkeit, die das Kopieren verbietet ...? Nun, nein. )

Schauen wir uns den Inhalt von [int (x * max_num) für x in wv] mit wv * = W, * x * = "jedes der untergeordneten Elemente von W" = w * an. In jedem untergeordneten Element w von W, x * max_num =x * 32767.0 / max(wv)

Welche Nummer ist 32767! Ich denke du verstehst. Dies liegt daran, dass die möglichen Werte von 16-Bit-Daten (Daten in 16-stelligen Binärzahlen ausgedrückt) * -32768 bis 32767 * sind. (2 bis 16 Potenz ist 65536, und die Hälfte von ihnen ist 32768, also ... ich bin verrückt)

Und der Binärcode "bi_wv = struct.pack (" h "* len (wv16), * wv16)". Um ehrlich zu sein, weiß ich nichts darüber. Dies ist eine Kopie. Derzeit konvertiert die Struktur binär struct.pack sie in das Binärformat, und das erste Argument" h " scheint ein 2-Byte-Ganzzahlformat (16 Bit) zu sein. Hallo.

Ja, die Binärisierung ist abgeschlossen!

2. WAV-Datei mit Wave-Modul ausgeben

Ich werde die Antwort zuerst noch einmal einfügen.

python


file = wave.open('sin_wave.wav', mode='wb') #sin_wave.Öffnen Sie wav im Schreibmodus. (Wenn die Datei nicht vorhanden ist, erstellen Sie eine neue.)
param = (1,2,sample_hz,len(bi_wv),'NONE','not compressed') #Parameter
file.setparams(param) #Parametereinstellung
file.writeframes(bi_wv) #Daten schreiben
file.close #Datei schließen

Es ist so. Öffnen Sie die Datei mit wave.open (). Geben Sie den Namen der Datei mit dem ersten Argument an und legen Sie den Schreibmodus ("wb") oder den Lesemodus ("rb") mit dem zweiten Argument "mode =" fest.

Stellen Sie die Parameter der WAV-Datei mit wave.setparams () ein. Die Parameter (param) sind in der Reihenfolge von links angeordnet

ist. Schreiben Sie dann die binärisierten Daten (bi_wv) und schließen Sie die Datei. Es ist leicht zu vergessen, die Datei zu schließen ...

Okay, es ist geschafft! !! (Versuchen Sie, die Datei auf Ihrem Terminal oder an der Eingabeaufforderung auszuführen, um festzustellen, ob eine WAV-Datei generiert wurde!)

Kapitel 3. Ich möchte einen Ton auf dem Programm machen, weil es nervt!

Öffnen Sie also zuerst die zuvor mit dem Wave-Modul erstellte Datei.

python


file = wave.open('sin_wave.wav', mode='rb')

Jetzt können Sie es öffnen. Sie befinden sich ordnungsgemäß im Lesemodus. Der file Teil von file = wave.open ('sin_wave.wav', mode = 'rb') stellt eine Variable dar, sodass Sie einen anderen Namen verwenden können. fairu oder wave_no_kiwami_otome oder was auch immer. Nun, ich habe es gerade gesagt. Musste ich als Anfänger "Datei" nennen? Weil ich falsch verstanden habe.

Spielen Sie dann den Sound mit dem Pyaudio-Modul.

python


p = pyaudio.PyAudio() #Instanziierung von Pyaudio
stream = p.open(
    format = p.get_format_from_width(file.getsampwidth()),
    channels = wr.getnchannels(),
    rate = wr.getframerate(),
    output = True
    ) #Erstellen Sie einen Stream zum Aufnehmen und Abspielen von Sounds.
file.rewind() #Bewegen Sie den Zeiger zurück zum Anfang.
chunk = 1024 #Ich bin nicht sicher, aber die offizielle Dokumentation hat dies getan.
data = file.readframes(chunk) #Lesen Sie Blöcke (1024) von Frames (Schallwellenformdaten).
while data:
    stream.write(data) #Machen Sie einen Ton, indem Sie Daten in den Stream schreiben.
    data = file.readframes(chunk) #Laden Sie einen neuen Blockrahmen.
stream.close() #Schließen Sie den Stream.
p.terminate() #Schließen Sie PyAudio.

Wie oben ist das Verfahren 1. Pyaudio öffnen, 2. Stream öffnen, 3. Daten zum Streamen schreiben und Sound abspielen, 4. Stream schließen, 5. Pyaudio schließen Es ist wie es ist.

Kapitel 4. Wellenanzeige

Nun, wie lange ein Artikel dauern würde. Ich bin müde, Patrasche. Deshalb habe ich den Code als Burn eingefügt.

python


pl.plot(t,wv)
pl.show()

Wie einfach! matplotlib.pyplot hat viele Artikel, daher werde ich nichts Besonderes sagen.

Am Ende

Danke, dass Sie so weit gelesen haben! Ich habe mein Bestes für den zweiten Qiita-Artikel in meinem Leben gegeben ...

Kann ich trotzdem wirklich selbst eine Software für die künstliche Sprachsynthese erstellen?

Referenzstelle / Literatur

Endgültiger Code

python


import numpy as np
import matplotlib.pyplot as pl
import wave
import struct
import pyaudio

#Chapter1
sec = 1 #1 Sekunde
note_hz = 440 #La Schallfrequenz
sample_hz = 44100 #Abtastfrequenz
t = np.arange(0, sample_hz * sec) #Sichern Sie sich eine Zeitspanne von 1 Sekunde
wv = np.sin(2 * np.pi * note_hz * t/sample_hz)


#Chapter2
max_num = 32767.0 / max(wv) #Vorbereitung für die Binärisierung
wv16 = [int(x * max_num) for x in wv] #Vorbereitung für die Binärisierung
bi_wv = struct.pack("h" * len(wv16), *wv16) #Binär

file = wave.open('sin_wave.wav', mode='wb') #sin_wave.Öffnen Sie wav im Schreibmodus. (Wenn die Datei nicht vorhanden ist, erstellen Sie eine neue.)
param = (1,2,sample_hz,len(bi_wv),'NONE','not compressed') #Parameter
file.setparams(param) #Parametereinstellung
file.writeframes(bi_wv) #Daten schreiben
file.close #Datei schließen

#Chapter3
file = wave.open('sin_wave.wav', mode='rb')

p = pyaudio.PyAudio()
stream = p.open(
    format = p.get_format_from_width(file.getsampwidth()),
    channels = file.getnchannels(),
    rate = file.getframerate(),
    output = True
    )
chunk = 1024
file.rewind()
data = file.readframes(chunk)
while data:
    stream.write(data)
    data = file.readframes(chunk)
stream.close()
p.terminate()

#Chapter4
pl.plot(t,wv)
pl.show()

Recommended Posts

Erklären Sie ausführlich, wie Sie mit Python einen Sound erzeugen
So arbeiten Sie mit BigQuery in Python
[REAPER] Wie man Reascript mit Python spielt
Wie man tkinter mit Python in Pyenv benutzt
So nehmen Sie Python Interpreter-Änderungen in Pycharm vor
Umgang mit Sounds in Python
Wie man in Python entwickelt
So konvertieren / wiederherstellen Sie einen String mit [] in Python
So führen Sie eine Hash-Berechnung mit Salt in Python durch
So führen Sie Tests zusammen mit Python unittest aus
[Python] Wie man PCA mit Python macht
So sammeln Sie Bilder in Python
Verwendung von SQLite in Python
Erste Schritte mit Python
Wie man MySQL mit Python benutzt
So verpacken Sie C in Python
Verwendung von ChemSpider in Python
Verwendung von PubChem mit Python
So berechnen Sie das Datum mit Python
Umgang mit Japanisch mit Python
So extrahieren Sie einen Termin in Google Kalender mit Python
So melden Sie sich mit Python bei AtCoder an und senden automatisch
Wie man mit Python-Installationsfehlern in pyenv umgeht (BUILD FAILED)
[Einführung in Python] Wie verwende ich eine Klasse in Python?
Wie man Japanern nicht entgeht, wenn man mit json in Python umgeht
Dynamisches Definieren von Variablen in Python
[Python] Wie man eine Klasse iterierbar macht
So machen Sie R chartr () in Python
So machen Sie einen String in Python zu einem Array oder ein Array zu einem String
[Itertools.permutations] So löschen Sie eine Sequenz in Python
Fraktal zum Erstellen und Spielen mit Python
So erstellen Sie eine Überwachungskamera (Überwachungskamera) mit Opencv und Python
So verwenden Sie Python in Pyenv unter MacOS mit PyCall
Wie bekomme ich Stacktrace in Python?
So zeigen Sie die neunundneunzig Tabelle in Python an
So extrahieren Sie einen Polygonbereich in Python
Wie man einen Taschentest mit Python macht
So überprüfen Sie die Version von opencv mit Python
So zeigen Sie Python-Japanisch mit Lolipop an
So wechseln Sie die Python-Version in Cloud9
So passen Sie den Bildkontrast in Python an
Verwendung von __slots__ in der Python-Klasse
Wirf etwas mit Python in Kinesis und stelle sicher, dass es drin ist
So füllen Sie mit Python dynamisch Nullen aus
Wie man mit Python-Flüchen Japanisch eingibt
So betreiben Sie die Zeitstempelstation in Python
Verwendung regulärer Ausdrücke in Python
So zeigen Sie Hello World in Python an
Verwendung ist und == in Python
Anzeigen von Legendenmarkierungen in einem mit Python 2D-Plot
Wie schreibe ich Ruby to_s in Python
So installieren Sie Python3 mit Docker Centos
So berechnen Sie "xx time" in einem Schuss mit Python timedelta
So ermitteln Sie mit Python den Unterschied zwischen Datum und Uhrzeit in Sekunden
Ich möchte die abstrakte Klasse (ABCmeta) von Python im Detail erklären
Was tun, wenn die Python-Version in Cloud 9 von einer anderen Person erstellt wurde?
Hochladen mit Heroku, Flask, Python, Git (4)