Skip to content

Instantly share code, notes, and snippets.

@suzuki-hoge
Last active December 7, 2020 11:03
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save suzuki-hoge/81f33f2b16f39761b03ca824c23d6210 to your computer and use it in GitHub Desktop.
Save suzuki-hoge/81f33f2b16f39761b03ca824c23d6210 to your computer and use it in GitHub Desktop.
吹奏楽部と純正律と平均律 本文

はじめに

ディズニーといえば、吹奏楽部時代に演奏会の〆によく「小さな世界」を吹いてました

tuba なんですけど、まー白玉ばっかりのロングトーンばっかの譜面で、「基礎練かよ」って譜面だったんですよね
それを 2h - 3h 吹いた後にやるもんだから「はよおわれ...」って思ってました

なんてことを思い出したので、たまには IT 離れて音楽っぽい話でもしようかと思います

吹奏楽部がどんなことを練習しているのかあんまり聞いたことないと思うので、面白く読んでもらえると嬉しいです

ウンチク垂れ流しなので、興味がない人はここまでで大丈夫ですw
明日の人に期待してくださいw

謝罪
 なんか僕自身が書いてたら楽しくなってしまって、いつも通り 長いです
 序盤でこれはやっちまったかなと思ってますが...
 書いてる人が楽しけりゃ何でも良いと思うんで、気楽にバトンしましょ

基本

  • ドレミファソラシドはそれぞれ C D E F G A B C とします
    • 特に区別する場合は下の C を C1, 上を C2 とします
  • E と F は黒鍵が挟まらないのでお隣さんです
    • 半音 1 つと言います
  • C と D は黒鍵が挟まるのでお隣さんではありません
    • 半音 2 つで全音と言います

image

4 半音とか 7 半音とか言うので、鍵盤画像を参考にどうぞ

周波数の話

理科の授業で遥か昔やった通り、弦の長さを半分にすると、周波数が倍になって高い音が出ます

この「周波数が倍」で 1 オクターブが作れます

この 1 オクターブの中をどうやって埋めてくかって話が、大きく分けて2つあります

純正律

基本

周波数の比率をシンプルな整数比で作ろうぜって音律です

C1 → C2 の周波数の比率が 2/1 でしたが、これは C1 の周波数を 2/1 倍にすると C2 になるという意味です
これ以外に C → E を 5/4 倍で, C → G を 3/2 倍で作ります

C → E の様に 4 半音あげたければ 5/4 倍, C → G の様に 7 半音あげたければ 3/2 倍するってことですね

E と G を C の整数比から作ったので、C, E, G を同時に鳴らした時の周波数が綺麗に鳴るのがメリットです

他の音も作れます

例えば B は G の 4 半音上なので、G ( 3/2 ) の 5/4 倍にすると作れます、C に対して 15/8 倍の周波数ということです
ほぼ 2/1 なので感覚的には合ってますね

D はまず G の 7 半音上の D2 ( 3/2 * 3/2 = 9/4 ) を作って、 1 オクターブ下げるために周波数を半分 (9/4 * 1/2 = 9/8 ) にして作ります
これもだいたい 1/1 なので感覚的には合ってますね

ちょっとアニメ付きで音律を埋めていく様を見てみます

just_intonation

できましたね

これは C に対して何倍の周波数にすれば良いか、って表です

-----------------------------------------------------------------------------------------
    C    |    D    |    E    |    F    |    G    |    A    |    B    |    C    |    D
-----------------------------------------------------------------------------------------
   1/1   |   9/8   |   5/4   |   4/3   |   3/2   |   5/3   |  15/8   |   2/1   |   9/4
-----------------------------------------------------------------------------------------

ここに出ている音で作れる長三和音 ( Major ) は 3 つあります、ちょっと確認してみると...

C : E : G  |  1/1 :  5/4 : 3/2  |  4/4 :  5/4 :  6/4
F : A : C  |  4/3 :  5/3 : 2/1  |  4/3 :  5/3 :  6/3
G : B : D  |  3/2 : 15/8 : 9/4  | 12/8 : 15/8 : 18/8

長三和音は周波数比が全部 4 : 5 : 6 で作れていますね、この和音はすごい綺麗です

綺麗に鳴るのは整数比だと周期が合う箇所が多いからだと思います
3 つの音がきっちり重なるポイントが多い方が、ノイズが混じりづらいってことなんでしょうね

実際に 4 : 5 : 6 の最小公倍数は 60 ですが、例えば 4 : 5.1 : 6 の最小公倍数は 204 です
「ピタリと合ってる」か「ニアミスでちょいズレ」のどっちが多くなるかで決まると言って良いでしょう

image (絵は適当)

とにかく、4 : 5 : 6 で和音を作ると綺麗なんです!(字で表現できないので押し通す)
(これはちょっともう聞く訓練をしまくるしかないけど...きっちりやると「みょんみょんみょんみょん...」ってのが鳴らなくなります アプリとかあるのかな? 交互に聴くと案外わかります)

なんにせよ、なんか良さげな音律ですね?

問題

そんなうまくいくかと言うと、いかないんですね

C → D と D → E を見てください

D → E の差分は E ( 5/4 ) / D ( 9/8 ) = 40/36 = 10/9 です

どっちも全音幅なのに、C → D の差 ( 9/8 ) と微妙に違いますね

実はこいつら、等間隔に並んでません

ちょっと確認してみましょう

from fractions import Fraction as F

def show(fs, ls, x):
    for i in range(1, len(fs)):
        print '%s → %s : ' % (ls[i - 1], ls[i]),
        print fs[i] / fs[i - 1]

show([F(1, 1), F(9, 8), F(5, 4), F(4, 3), F(3, 2), F(5, 3), F(15, 8), F(2, 1)], 'CDEFGABC', 48)
C → D :  9/8
D → E :  10/9
E → F :  16/15
F → G :  9/8
G → A :  10/9
A → B :  9/8
B → C :  16/15 

ちょっと見やすくしたり通分したりします

ちなみに、9/8 の差が出てるところを大全音 ( T ) と言い、10/9 の差が出ているところを小全音 ( t ) と言います
半音は s です

C
    405/360 ( T )
D
    400/360 ( t )
E
    384/360 ( s )
F
    405/360 ( T )
G
    400/360 ( t )
A
    405/360 ( T )
B
    384/360 ( s )
C
    405/360 ( T )
D

これを見ると、C → D に対して D → E の変動が少ないので、E は D ほど上がりきれていない、つまり E は低い んです
G → A にかけても同じです
A → B は問題なさそうに見えますが、基準値となった A がそもそも低いので B も低い です

逆に 3 つの長三和音を構成する C → E, F → A, G → B はいずれも T * t で、
E → G, A → C, B → D はいずれも s * T で作れているので、長三和音は寸分の狂いもない です

まぁとにかく、この音律でメロディーを演奏したりすると、変な感じになります
というかそもそも長三和音以外ほぼガタガタです

そもそもこれは C の純正律 なので、キーが E の曲をやるなら E の純正律を使わないとだめです

メンドクセーー

平均律

そこでこいつです

基本

シンプルです

きっちり 12 等分しようぜ、って音律です

半音あげるには 1.059463 倍、全音あげるには 1.122462 ( 1.059463 * 1.059463 ) 倍、これだけです

こっちも見てみます

equal_temperament

できました

-------------------------------------------------------------------------------
    C    |    D    |    E    |    F    |    G    |    A    |    B    |    C
-------------------------------------------------------------------------------
  1.000  |  1.122  |  1.259  |  1.334  |  1.498  |  1.681  |  1.887  |  2.000
-------------------------------------------------------------------------------

これ見てもよくわからないので、ちょっと純正律と平均律の diff を取ってみます

上から「純正律(分数)」「純正律(小数)」「平均律」「周波数差 ( cent )」です

-------------------------------------------------------------------------------
    C    |    D    |    E    |    F    |    G    |    A    |    B    |    C    
-------------------------------------------------------------------------------
   1/1   |   9/8   |   5/4   |   4/3   |   3/2   |   5/3   |  15/8   |   2/1   
-------------------------------------------------------------------------------
  1.000  |  1.125  |  1.250  |  1.333  |  1.500  |  1.666  |  1.875  |  2.000  
-------------------------------------------------------------------------------
  1.000  |  1.122  |  1.259  |  1.334  |  1.498  |  1.681  |  1.887  |  2.000
-------------------------------------------------------------------------------
    0    |  -3.69  |  13.69  |   1.96  |  -1.96  |  15.64  |  11.73  |    0  
-------------------------------------------------------------------------------

やっぱ 純正律の E 低いですね
等間隔だと C に対して 1.259 倍なのに、純正律では 1.250 倍しかしてません

A と B も同じくらいずれてますね

使い分け

基本的に和音は純正律で、メロディーは平均律で、みたいな感じが理想です

吹奏楽部の人は絶対一度は「あんたは三音だから 13.7 cent 下げなさい」って和音練習で言わたと思いますが、こういうことだったんですねー

吹奏楽部の人って

なので「この E は C Major の三音だから -13.7」「この E は E Major の根音だから ±0」とかを考えなきゃいけないわけです

ちなみに周波数の単位 cent ですが、100 cent で半音変わります
なので 13.7 cent は結構シビアです、キビシー

image

メモリが cent で -50 ~ +50 です
このメモリを「自分が何の和音の何音目か」考えて -13 にしたり 0 にしたりするんです
まぁ僕はベースだったので 99% は根音で、±0 きっちりマシーンと化してました

僕は cent 調整は超得意でした
「お前らはチューナー使ってるから耳が悪いんだよ」とか言ってチューナー持ち歩いてなかったなー
おーかっこいいねー  んふふふふ

とにかく、吹部って校庭走ってフィンガートレーニングしてるだけじゃあないんだよ
(僕走ったことないので走る吹部って都市伝説だと思ってるけどw)

ちょっとはイメージ湧きましたか?

おしまい

以上ですw

いつも通り垂れ流すだけの記事になりました、ここまで読んだ人がいるかは不明です

実はこれ、高校の時に僕のクラスがなんかすげぇ特進クラスで、いろんな「研究」ってコマがあったのでやったんですよね
なんか機材使って周波数可視化とかまでやったり、(ちゃちな)論文の1ページ目だけ英語で書かされたりしたのを思い出しました

まぁ僕のクラスは他に吹部いなかったし、吹部にもこんなこと考えてるやつほとんどいなかったしで、当時でさえ「は?」ってなったのは想像に難くないですね

今もなってるかな?
もしそうならクソポエマ冥利に尽きますね、タマンネー

import os, time
class Table:
def __init__(self, col_w, headers, cols):
self.col_w = col_w
self.headers = headers
self.length = col_w * len(headers) + 1 * (len(headers) - 1)
self.cols = cols
def anime(self, s, e, message, col):
os.system('clear')
self.show_table()
print ' '
time.sleep(1)
os.system('clear')
self.show_table()
if s < e:
self.show_message_r(s, e, message)
else:
self.show_message_l(s, e, message)
self.cols[e] = col
time.sleep(1)
os.system('clear')
self.show_table()
print ' '
def show_table(self):
print '-' * self.length
print '|'.join(map(lambda h: h.center(self.col_w, ' '), self.headers))
print '-' * self.length
print '|'.join(map(lambda c: c.center(self.col_w, ' ') if len(c) % 2 == 1 else c.center(self.col_w - 1, ' ') + ' ', self.cols))
print '-' * self.length
def show_message_r(self, s, e, message):
space = ' ' * (self.col_w / 2) + ' ' * (s * (self.col_w + 1))
bar = '-' * ((e - s) * (self.col_w + 1) - (len(message) / 2 + 2))
arrow = bar + '>'
print '%(space)s%(arrow)s %(message)s' % locals()
def show_message_l(self, s, e, message):
space = ' ' * (self.col_w / 2) + ' ' * (e * (self.col_w + 1)) + ' ' * len(message)
bar = '-' * ((s - e) * (self.col_w + 1) - len(message))
message = message.rjust(len(space) - 1, ' ')
arrow = '<' +bar
print '%(message)s %(arrow)s' % locals()
from table import Table
table = Table(9, 'CDEFGABCD', ['1/1', '', '', '', '', '', '', '', ''])
table.anime(0, 2, '5/4', '5/4')
table.anime(0, 4, '3/2', '3/2')
table.anime(4, 6, '5/4', '15/8')
table.anime(4, 8, '3/2', '9/4')
table.anime(8, 1, '1/2', '9/8')
table.anime(0, 7, '2/1', '2/1')
table.anime(7, 3, '2/3', '4/3')
table.anime(3, 5, '5/4', '5/3')
from table import Table
table = Table(9, 'CDEFGABC', ['1.000', '', '', '', '', '', '', ''])
table.anime(0, 1, '1.122', '1.122')
table.anime(1, 2, '1.122', '1.259')
table.anime(2, 3, '1.059', '1.334')
table.anime(3, 4, '1.122', '1.498')
table.anime(4, 5, '1.122', '1.681')
table.anime(5, 6, '1.122', '1.887')
table.anime(6, 7, '1.059', '2.000')
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment