-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathmel.go
58 lines (50 loc) · 1.29 KB
/
mel.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
// Copyright 2018 The ZikiChombo Authors. All rights reserved. Use of this source
// code is governed by a license that can be found in the License file.
package freq
import (
"fmt"
"math"
)
// Mel is a unit of frequency in which a difference less than MelAudible
// is generally imperceivable (melodically). See https://en.wikipedia.org/wiki/Mel_scale
type Mel int64
// MelAudible is the smallest difference in frequency in Mels which
// is melodically audible. Smaller harmonic differences are audible
// due to beating.
const MelAudible Mel = Mel(1000000000)
// ToMel gives f in Mels.
func ToMel(f T) Mel {
sign := int64(1)
if f < 0 {
f = -f
sign = -1
}
hz := f.Float64()
v := 1.0 + hz/700.0
v = 2595 * math.Log10(v)
m := sign * int64(math.Floor(v+0.5)) * int64(MelAudible)
return Mel(m)
}
// String returns a string representation of m.
func (m Mel) String() string {
return fmt.Sprintf("%d.%03dmel", m/MelAudible, (m%MelAudible)/Mel(MilliHertz))
}
// FromMel gives m as frequency.
func FromMel(m Mel) T {
return m.Freq()
}
// Freq gives m as frequency.
func (m Mel) Freq() T {
sign := int64(1)
if m < 0 {
m = -m
sign = -1
}
v := float64(int64(m) / int64(Hertz))
v /= 2595
v = math.Pow(10, v)
v -= 1
v *= 700
f := sign * int64(math.Floor(v+0.5)) * int64(Hertz)
return T(f)
}