数式での翻訳 |
---|
\(\textrm{Octave} = \mathbb{Z}\)と置き、\(\textrm{Octave}\)の元をオクターブと呼びます。音名とオクターブの文字列としての結合で与えられる文字列を、音名とオクターブの組と同一視します。音名とオクターブの組全体の集合 \[ \textrm{Pitch} = \textrm{OnMei} \times \textrm{Octave} \] に属する文字列をピッチと呼びます。例えば音名の記事で述べたように幹音である文字列\(\textrm{La}\)は音名\((\textrm{La},\textrm{□})\)と同一視され、更に文字列\(\textrm{La}4\)は組\((\textrm{La},4)\)と同一視されることから、\(\textrm{La}4\)はピッチとなります。
第\(1\)射影と第\(2\)射影 \[ \begin{align} \textrm{Pitch} & \to \textrm{OnMei} \\
\textrm{Pitch} & \to \textrm{Octave} \end{align} \] をそれぞれ\(\textrm{GetOnMei}\)と\(\textrm{GetOctave}\)と置きます。
\(\textrm{NoteNumber} = \mathbb{Z}\)と置き、\(\textrm{NoteNumber}\)の元をノートナンバーと呼びます。全射な写像 \[ \begin{align} \textrm{GetNoteNumber} \colon \textrm{Pitch} & \to \textrm{NoteNumber} \\
P & \mapsto \textrm{Represent}(\textrm{GetPitchClass}(\textrm{GetOnMei}(P))) + 12(\textrm{GetOctave}(P)+1) \end{align} \] を用いて写像 \[ \begin{align} \textrm{GetShuuHaSuu} \colon \textrm{Pitch} & \to \mathbb{R} \\
P & \mapsto \textrm{GetShuuHaSuu}(P) \end{align} \] を \[ \textrm{GetShuuHaSuu}(P) = 440 \times 2^{\frac{\textrm{GetNoteNumber}(P) - \textrm{GetNoteNumber}(\textrm{La}4)}{12}} \] と定め、\(\textrm{GetShuuhasuu}(P)\)を\(P\)の表す周波数と呼びます。
更に写像 \[ \textrm{GetPitchClass} \colon \textrm{Pitch} \to \textrm{PitchClass} \] を写像\(\textrm{GetOnMei} \colon \textrm{Pitch} \to \textrm{OnMei}\)と\(\textrm{GetPitchClass} \colon \textrm{OnMei} \to \textrm{PitchClass}\)の合成としてオーバーロードします。写像\(\textrm{GetPitchClass} \colon \textrm{Pitch} \to \textrm{PitchClass}\)は全射であるため\(\textrm{PitchClass}\)は\(\textrm{Pitch}\)の商集合と同一視することができ、特に各ピッチクラスはピッチの同値類とみなすことができます。
C++での宣言 |
---|
ピッチのクラスおよび関係する関数たちを以下のように宣言します。
using Octave = int;
using NoteNumber = int;
class Pitch
{
private:
OnMei m_N;
Octave m_octave;
static constexpr const Octave g_La4_notenumber = 69;
static constexpr const double g_La4_shuuhasuu = 440.0;
public:
inline Pitch( const OnMei& N , const Octave& octave ) noexcept;
Pitch& operator++() noexcept;
Pitch& operator--() noexcept;
inline NoteNumber GetNoteNum() const noexcept;
inline const OnMei& GetOnMei() const noexcept;
inline const Octave& GetOctave() const noexcept;
inline double GetShuuHaSuu() const noexcept;
inline PitchClass GetPitchClass() const noexcept;
inline string Display() const noexcept;
};
inline bool operator==( const Pitch& N1 , const Pitch& N2 ) noexcept;
inline bool operator!=( const Pitch& N1 , const Pitch& N2 ) noexcept;
C++での定義 |
---|
実際の実装例についてはこちらをご覧下さい。実装においては以下の仕様を要請します。
inline Pitch::Pitch( const OnMei& N , const Octave& octave ) noexcept
はメンバ初期化子リストm_N( N )
,m_octave( octave )
で定める。Pitch& Pitch::operator++() noexcept
とPitch& Pitch::operator--() noexcept
はそれぞれ++m_N
と--m_N
を実行し、return *this
と定める。inline NoteNumber Pitch::GetNoteNum() const noexcept
はreturn ( m_N.GetPitchClass() ).Represent() + ( ( m_octave + 1 ) * 12 )
と定める。inline const OnMei& Pitch::GetOnMei() const noexcept
はreturn m_N
と定める。inline const Octave& Pitch::GetOctave() const noexcept
はreturn m_scale
と定める。inline double Pitch::GetShuuHaSuu() const noexcept
はreturn g_La4_shuuhasuu * pow( 2.0 , ( GetNoteNumber() - g_La4_notenumber ) / 12.0 )
と定める。inline PitchClass Pitch::GetPitchClass() const noexcept
はreturn m_N.GetPitchClass()
と定める。inline string Pitch::Display() const noexcept
はreturn m_N.Display() + to_string( m_octave )
と定める。- クラス
Pitch
に対する等号演算子は自然なものである。