トップ «前の日記(2009-02-19) 最新 次の日記(2009-02-21)» 編集

日々の破片

Subscribe with livedoor Reader
著作一覧

2009-02-20

_ 今読んでいる本

音をプログラムから扱う方法で、MIDIは大体わかるしそれなりにプログラムも組んでいるわけだが、なんというか、自由度が低くてつまらない。 別に楽音だけで遊ぶ必要もないわけなので、波の音を使ってみたいのだが、知らないものは知らないので、なんか本でも読んでみるか、とジャスコの3階の本屋で見かけたので買ってみた。

WAVプログラミング―.NET C#で学ぶ音響処理(北山 洋幸)

うーん、値段のわりに微妙というか、ちゃんと読まずに買ったおれも悪いのだろうが、半分ほどは20分もかからずに読み終わってしまった。

最初にwavファイルのフォーマットについて説明がある。なるほど、そうなのか。というところまでは良い。C#を使うけど、単純にBinaryStreamを使って上から下へプログラムを流すぜ、というのも本で読むには悪いスタイルではなく、むしろ読みやすいからこれもOK。

しかし、右チャネルを無音にする。左チャネルを無音にする、交互に無音にする、という1〜2行違うだけの見開き2ページくらいのプログラムがえんえんと続くのにはいささかまいった。

で、ようやく、16ビットのwavファイルを8ビットに変換する、という少しはそれっぽい処理が出て来て、見ると、これまた1行(ヘッダの書き出しは別として)違う。

で、その式が(引用ではなくコードを思い出しながら書いている)、short L = binstream.readShort(); deststream.writeByte((byte)((L >> 8) + 128))というような処理で、なぜ、16ビットを8ビット右シフトして128足して下の1バイトを取り出すことで変換できるんだ? と不思議になる。(実際にwavファイルを変換して聴けば良いのだが、電車の中で読んでいたのでそれは無理。というか、今やればよいので後で試す)

(細かなことを言い出すと、型の使い方が不自然な気がするが、Javaと違ってC#のbyteは符号なしだからか、というかsbyteを使わないのはなぜだろうか、とか)

1バイトは-128〜127で、2バイトなら-32768〜32767だ(と書いて、少し怪しいことに気づく。irbだとこの辺がちょっと弱いな。Bignumは万能ではない)

16ビットを8ビットにするというのだから、全体の間隔を間引く必要があるんじゃないかな、ということだ。

実際に、この式を利用して16ビット整数を8ビット整数に変えるとこんな感じになる。

public class b16 {
    public static void Main() {
        int[] ss =  { 0x8000, 0xf000, 0xff00, 0, 1, 0xff, 0xfff, 0x7fff };
        foreach (int s in ss) {
            System.Console.WriteLine("{0} -> {1}", (short)s, (sbyte)((s >> 8) + 128));
        }
    }
}
実行すると
-32768 -> 0
-4096 -> 112
-256 -> 127
0 -> -128
1 -> -128
255 -> -128
4095 -> -113
32767 -> -1

どうにも腑に落ちない。なんともアナログから取り出した数は不思議な世界だな。というわけで実際にやってみるか

追記:試そうと思ったがwavファイルなんてどこにも入ってないじゃん。今のWindowsはサンプルもwmaなのか……この後に本題のカラオケ用に中音を抜くとか、エコーをかけるとかの加工の話に入るので、何かwavファイルを入手しないとどうしようもないなぁ

本日のツッコミ(全7件) [ツッコミを入れる]
_ mamamoto (2009-02-20 10:20)

たしか8bitのときはunsignedで16bitの時はsignedっていう仕様だった気が。<br><br>手前味噌ですがrubyで簡単なwav作るコードを書いたことがあります。<br>http://d.hatena.ne.jp/mamamoto/20081023/1224737235

_ arton (2009-02-20 22:26)

確かにそうみたいですね(本でも書いてありました)。でも原点をどこにとるかの言い方の問題のような。<br>それはそれとしてクロスオーバーものはおもしろいですよね。

_ mamamoto (2009-02-23 14:07)

遅ればせてるのでもう解決してるかもしれないですが。<br><br>>1バイトは-128〜127で、2バイトなら-32768〜32767<br>ではなくて、1バイトの時は0〜255の範囲で波を作ります。<br><br>実際に、のコードのキャストの部分を(byte)((s >> 8) + 128))ってbyteに変えて実行すると、<br><br>gmcs wav.cs && mono wav.exe<br>-32768 -> 0<br>-4096 -> 112<br>-256 -> 127<br>0 -> 128<br>1 -> 128<br>255 -> 128<br>4095 -> 143<br>32767 -> 255<br><br>ってなるので本はあってるのかなーと。<br>それはそれとして見てのようにmonoとかも好きなものの一つです。

_ arton (2009-02-24 01:19)

どうもありがとうございます。なるほど、unsignedにすると一目瞭然ですね。

_ Craf (2009-02-26 20:10)

今更ながら<br>C:\Windows\Media\ に、Windowsの効果音のwavファイルが入ってます。

_ arton (2009-02-26 20:19)

なるほど。そういえば効果音がありました。どうもありがとうございます。

_ Craf (2009-02-26 20:34)

考えてみたらiTunesとかでも、CDからWave形式でインポートする設定ができました。<br>一昔前はCDリッピングはWaveファイルが普通でしたが、今じゃ普通の人は使わないファイル形式なんでしょうね。


2003|06|07|08|09|10|11|12|
2004|01|02|03|04|05|06|07|08|09|10|11|12|
2005|01|02|03|04|05|06|07|08|09|10|11|12|
2006|01|02|03|04|05|06|07|08|09|10|11|12|
2007|01|02|03|04|05|06|07|08|09|10|11|12|
2008|01|02|03|04|05|06|07|08|09|10|11|12|
2009|01|02|03|04|05|06|07|08|09|10|11|12|
2010|01|02|03|04|05|06|07|08|09|10|11|12|
2011|01|02|03|04|05|06|07|08|09|10|11|12|
2012|01|02|03|04|05|06|07|08|09|10|11|12|
2013|01|02|03|04|05|06|07|08|09|10|11|12|
2014|01|02|03|04|05|06|07|08|09|10|11|12|
2015|01|02|03|04|05|06|07|08|09|10|11|12|
2016|01|02|03|04|05|06|07|08|09|10|11|12|
2017|01|02|03|04|05|06|07|08|09|10|11|12|
2018|01|02|03|04|05|06|07|08|

ジェズイットを見習え