gonum.org/v1/gonum@v0.14.0/dsp/window/window.go (about) 1 // Copyright ©2020 The Gonum Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package window 6 7 import "math" 8 9 // Rectangular modifies seq in place by the Rectangular window and returns 10 // the result. 11 // See https://en.wikipedia.org/wiki/Window_function#Rectangular_window and 12 // https://www.recordingblogs.com/wiki/rectangular-window for details. 13 // 14 // The rectangular window has the lowest width of the main lobe and largest 15 // level of the side lobes. The result corresponds to a selection of 16 // limited length sequence of values without any modification. 17 // 18 // The sequence weights are 19 // 20 // w[k] = 1, 21 // 22 // for k=0,1,...,N-1 where N is the length of the window. 23 // 24 // Spectral leakage parameters: ΔF_0 = 2, ΔF_0.5 = 0.89, K = 1, ɣ_max = -13, β = 0. 25 func Rectangular(seq []float64) []float64 { 26 return seq 27 } 28 29 // Sine modifies seq in place by the Sine window and returns the result. 30 // See https://en.wikipedia.org/wiki/Window_function#Sine_window and 31 // https://www.recordingblogs.com/wiki/sine-window for details. 32 // 33 // Sine window is a high-resolution window. 34 // 35 // The sequence weights are 36 // 37 // w[k] = sin(π*k/(N-1)), 38 // 39 // for k=0,1,...,N-1 where N is the length of the window. 40 // 41 // Spectral leakage parameters: ΔF_0 = 3, ΔF_0.5 = 1.23, K = 1.5, ɣ_max = -23, β = -3.93. 42 func Sine(seq []float64) []float64 { 43 k := math.Pi / float64(len(seq)-1) 44 for i := range seq { 45 seq[i] *= math.Sin(k * float64(i)) 46 } 47 return seq 48 } 49 50 // Lanczos modifies seq in place by the Lanczos window and returns the result. 51 // See https://en.wikipedia.org/wiki/Window_function#Lanczos_window and 52 // https://www.recordingblogs.com/wiki/lanczos-window for details. 53 // 54 // The Lanczos window is a high-resolution window. 55 // 56 // The sequence weights are 57 // 58 // w[k] = sinc(2*k/(N-1) - 1), 59 // 60 // for k=0,1,...,N-1 where N is the length of the window. 61 // 62 // Spectral leakage parameters: ΔF_0 = 3.24, ΔF_0.5 = 1.3, K = 1.62, ɣ_max = -26.4, β = -4.6. 63 func Lanczos(seq []float64) []float64 { 64 k := 2 / float64(len(seq)-1) 65 for i := range seq { 66 x := math.Pi * (k*float64(i) - 1) 67 if x == 0 { 68 // Avoid NaN. 69 continue 70 } 71 seq[i] *= math.Sin(x) / x 72 } 73 return seq 74 } 75 76 // Triangular modifies seq in place by the Triangular window and returns 77 // the result. 78 // See https://en.wikipedia.org/wiki/Window_function#Triangular_window and 79 // https://www.recordingblogs.com/wiki/triangular-window for details. 80 // 81 // The Triangular window is a high-resolution window. 82 // 83 // The sequence weights are 84 // 85 // w[k] = 1 - |k/A -1|, A=(N-1)/2, 86 // 87 // for k=0,1,...,N-1 where N is the length of the window. 88 // 89 // Spectral leakage parameters: ΔF_0 = 4, ΔF_0.5 = 1.33, K = 2, ɣ_max = -26.5, β = -6. 90 func Triangular(seq []float64) []float64 { 91 a := float64(len(seq)-1) / 2 92 for i := range seq { 93 seq[i] *= 1 - math.Abs(float64(i)/a-1) 94 } 95 return seq 96 } 97 98 // Hann modifies seq in place by the Hann window and returns the result. 99 // See https://en.wikipedia.org/wiki/Window_function#Hann_and_Hamming_windows 100 // and https://www.recordingblogs.com/wiki/hann-window for details. 101 // 102 // The Hann window is a high-resolution window. 103 // 104 // The sequence weights are 105 // 106 // w[k] = 0.5*(1 - cos(2*π*k/(N-1))), 107 // 108 // for k=0,1,...,N-1 where N is the length of the window. 109 // 110 // Spectral leakage parameters: ΔF_0 = 4, ΔF_0.5 = 1.5, K = 2, ɣ_max = -31.5, β = -6. 111 func Hann(seq []float64) []float64 { 112 k := 2 * math.Pi / float64(len(seq)-1) 113 for i := range seq { 114 seq[i] *= 0.5 * (1 - math.Cos(k*float64(i))) 115 } 116 return seq 117 } 118 119 // BartlettHann modifies seq in place by the Bartlett-Hann window and returns 120 // result. 121 // See https://en.wikipedia.org/wiki/Window_function#Bartlett%E2%80%93Hann_window 122 // and https://www.recordingblogs.com/wiki/bartlett-hann-window for details. 123 // 124 // The Bartlett-Hann window is a high-resolution window. 125 // 126 // The sequence weights are 127 // 128 // w[k] = 0.62 - 0.48*|k/(N-1)-0.5| - 0.38*cos(2*π*k/(N-1)), 129 // 130 // for k=0,1,...,N-1 where N is the length of the window. 131 // 132 // Spectral leakage parameters: ΔF_0 = 4, ΔF_0.5 = 1.45, K = 2, ɣ_max = -35.9, β = -6. 133 func BartlettHann(seq []float64) []float64 { 134 const ( 135 a0 = 0.62 136 a1 = 0.48 137 a2 = 0.38 138 ) 139 140 k := 2 * math.Pi / float64(len(seq)-1) 141 for i := range seq { 142 seq[i] *= a0 - a1*math.Abs(float64(i)/float64(len(seq)-1)-0.5) - a2*math.Cos(k*float64(i)) 143 } 144 return seq 145 } 146 147 // Hamming modifies seq in place by the Hamming window and returns the result. 148 // See https://en.wikipedia.org/wiki/Window_function#Hann_and_Hamming_windows 149 // and https://www.recordingblogs.com/wiki/hamming-window for details. 150 // 151 // The Hamming window is a high-resolution window. Among K=2 windows it has 152 // the highest ɣ_max. 153 // 154 // The sequence weights are 155 // 156 // w[k] = 25/46 - 21/46 * cos(2*π*k/(N-1)), 157 // 158 // for k=0,1,...,N-1 where N is the length of the window. 159 // 160 // Spectral leakage parameters: ΔF_0 = 4, ΔF_0.5 = 1.33, K = 2, ɣ_max = -42, β = -5.37. 161 func Hamming(seq []float64) []float64 { 162 const ( 163 a0 = 0.54 164 a1 = 0.46 165 ) 166 167 k := 2 * math.Pi / float64(len(seq)-1) 168 for i := range seq { 169 seq[i] *= a0 - a1*math.Cos(k*float64(i)) 170 } 171 return seq 172 } 173 174 // Blackman modifies seq in place by the Blackman window and returns the 175 // result. 176 // See https://en.wikipedia.org/wiki/Window_function#Blackman_window and 177 // https://www.recordingblogs.com/wiki/blackman-window for details. 178 // 179 // The Blackman window is a high-resolution window. 180 // 181 // The sequence weights are 182 // 183 // w[k] = 0.42 - 0.5*cos(2*π*k/(N-1)) + 0.08*cos(4*π*k/(N-1)), 184 // 185 // for k=0,1,...,N-1 where N is the length of the window. 186 // 187 // Spectral leakage parameters: ΔF_0 = 6, ΔF_0.5 = 1.7, K = 3, ɣ_max = -58, β = -7.54. 188 func Blackman(seq []float64) []float64 { 189 const ( 190 a0 = 0.42 191 a1 = 0.5 192 a2 = 0.08 193 ) 194 195 k := 2 * math.Pi / float64(len(seq)-1) 196 for i := range seq { 197 x := k * float64(i) 198 seq[i] *= a0 - a1*math.Cos(x) + a2*math.Cos(2*x) 199 } 200 return seq 201 } 202 203 // BlackmanHarris modifies seq in place by the Blackman-Harris window and 204 // returns the result. 205 // See https://en.wikipedia.org/wiki/Window_function#Blackman%E2%80%93Harris_window 206 // and https://www.recordingblogs.com/wiki/blackman-harris-window for details. 207 // 208 // The Blackman-Harris window is a low-resolution window. 209 // 210 // The sequence weights are 211 // 212 // w[k] = 0.35875 - 0.48829*cos(2*π*k/(N-1)) + 213 // 0.14128*cos(4*π*k/(N-1)) - 0.01168*cos(6*π*k/(N-1)), 214 // 215 // for k=0,1,...,N-1 where N is the length of the window. 216 // 217 // Spectral leakage parameters: ΔF_0 = 8, ΔF_0.5 = 1.97, K = 4, ɣ_max = -92, β = -8.91. 218 func BlackmanHarris(seq []float64) []float64 { 219 const ( 220 a0 = 0.35875 221 a1 = 0.48829 222 a2 = 0.14128 223 a3 = 0.01168 224 ) 225 226 k := 2 * math.Pi / float64(len(seq)-1) 227 for i := range seq { 228 x := k * float64(i) 229 seq[i] *= a0 - a1*math.Cos(x) + a2*math.Cos(2*x) - a3*math.Cos(3*x) 230 } 231 return seq 232 } 233 234 // Nuttall modifies seq in place by the Nuttall window and returns the result. 235 // See https://en.wikipedia.org/wiki/Window_function#Nuttall_window,_continuous_first_derivative 236 // and https://www.recordingblogs.com/wiki/nuttall-window for details. 237 // 238 // The Nuttall window is a low-resolution window. 239 // 240 // The sequence weights are 241 // 242 // w[k] = 0.355768 - 0.487396*cos(2*π*k/(N-1)) + 0.144232*cos(4*π*k/(N-1)) - 243 // 0.012604*cos(6*π*k/(N-1)), 244 // 245 // for k=0,1,...,N-1 where N is the length of the window. 246 // 247 // Spectral leakage parameters: ΔF_0 = 8, ΔF_0.5 = 1.98, K = 4, ɣ_max = -93, β = -9. 248 func Nuttall(seq []float64) []float64 { 249 const ( 250 a0 = 0.355768 251 a1 = 0.487396 252 a2 = 0.144232 253 a3 = 0.012604 254 ) 255 256 k := 2 * math.Pi / float64(len(seq)-1) 257 for i := range seq { 258 x := k * float64(i) 259 seq[i] *= a0 - a1*math.Cos(x) + a2*math.Cos(2*x) - a3*math.Cos(3*x) 260 } 261 return seq 262 } 263 264 // BlackmanNuttall modifies seq in place by the Blackman-Nuttall window and 265 // returns the result. 266 // See https://en.wikipedia.org/wiki/Window_function#Blackman%E2%80%93Nuttall_window 267 // and https://www.recordingblogs.com/wiki/blackman-nuttall-window for details. 268 // 269 // The Blackman-Nuttall window is a low-resolution window. 270 // 271 // The sequence weights are 272 // 273 // w[k] = 0.3635819 - 0.4891775*cos(2*π*k/(N-1)) + 0.1365995*cos(4*π*k/(N-1)) - 274 // 0.0106411*cos(6*π*k/(N-1)), 275 // 276 // for k=0,1,...,N-1 where N is the length of the window. 277 // 278 // Spectral leakage parameters: ΔF_0 = 8, ΔF_0.5 = 1.94, K = 4, ɣ_max = -98, β = -8.8. 279 func BlackmanNuttall(seq []float64) []float64 { 280 const ( 281 a0 = 0.3635819 282 a1 = 0.4891775 283 a2 = 0.1365995 284 a3 = 0.0106411 285 ) 286 287 k := 2 * math.Pi / float64(len(seq)-1) 288 for i := range seq { 289 x := k * float64(i) 290 seq[i] *= a0 - a1*math.Cos(x) + a2*math.Cos(2*x) - a3*math.Cos(3*x) 291 } 292 return seq 293 } 294 295 // FlatTop modifies seq in place by the Flat Top window and returns the 296 // result. 297 // See https://en.wikipedia.org/wiki/Window_function#Flat_top_window and 298 // https://www.recordingblogs.com/wiki/flat-top-window for details. 299 // 300 // The Flat Top window is a low-resolution window. 301 // 302 // The sequence weights are 303 // 304 // w[k] = 0.21557895 - 0.41663158*cos(2*π*k/(N-1)) + 305 // 0.277263158*cos(4*π*k/(N-1)) - 0.083578947*cos(6*π*k/(N-1)) + 306 // 0.006947368*cos(4*π*k/(N-1)), 307 // 308 // for k=0,1,...,N-1 where N is the length of the window. 309 // 310 // Spectral leakage parameters: ΔF_0 = 10, ΔF_0.5 = 3.72, K = 5, ɣ_max = -93.0, β = -13.34. 311 func FlatTop(seq []float64) []float64 { 312 const ( 313 a0 = 0.21557895 314 a1 = 0.41663158 315 a2 = 0.277263158 316 a3 = 0.083578947 317 a4 = 0.006947368 318 ) 319 320 k := 2 * math.Pi / float64(len(seq)-1) 321 for i := range seq { 322 x := k * float64(i) 323 seq[i] *= a0 - a1*math.Cos(x) + a2*math.Cos(2*x) - a3*math.Cos(3*x) + a4*math.Cos(4*x) 324 } 325 return seq 326 }