Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update to rustfft 6.0 and Rust 2018 edition #6

Open
wants to merge 13 commits into
base: master
Choose a base branch
from
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
target
**.DS_Store
Cargo.lock
.idea/
15 changes: 12 additions & 3 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,18 @@ name = "stft"
readme = "README.md"
repository = "https://github.com/snd/stft.git"
version = "0.2.0"
edition = "2018"

[dependencies]
apodize = "0.3.1"
num = "0.2.0"
rustfft = "3.0.0"
apodize = "1.0.0"
num = "0.4.0"
rustfft = "6.0.1"
strider = "0.1.3"

[dev-dependencies]
criterion = "0.3.4"
approx = "0.5.0"

[[bench]]
name = "lib"
harness = false
174 changes: 105 additions & 69 deletions benches/lib.rs
Original file line number Diff line number Diff line change
@@ -1,98 +1,134 @@
#![feature(test)]
extern crate test;

extern crate num;
use criterion::{criterion_group, criterion_main, Criterion};
use num::complex::Complex;

extern crate rustfft;
use rustfft::FFT;

extern crate stft;
use stft::{STFT, WindowType};
use rustfft::{FftDirection, FftPlanner};
use stft::{WindowType, STFT};

macro_rules! bench_fft_process {
($bencher:expr, $window_size:expr, $float:ty) => {{
let inverse = false;
let window_size = $window_size;
let mut fft = FFT::<$float>::new(window_size, inverse);
let input = std::iter::repeat(Complex::new(0., 0.))
.take(window_size)
.collect::<Vec<Complex<$float>>>();
($c:expr, $window_size:expr, $float:ty) => {{
let mut planner = FftPlanner::new();
let fft = planner.plan_fft($window_size, FftDirection::Forward);
// input is processed in-place
let mut output = std::iter::repeat(Complex::new(0., 0.))
.take(window_size)
.take($window_size)
.collect::<Vec<Complex<$float>>>();
$bencher.iter(|| {
fft.process(&input[..], &mut output[..])
});

}}
$c.bench_function(
concat!(
"bench_fft_process_",
stringify!($window_size),
"_",
stringify!($float)
),
|b| b.iter(|| fft.process(&mut output[..])),
);
}};
}

#[bench]
fn bench_fft_process_1024_f32(bencher: &mut test::Bencher) {
bench_fft_process!(bencher, 1024, f32);
fn bench_fft_process_1024_f32(c: &mut Criterion) {
bench_fft_process!(c, 1024, f32);
}

#[bench]
fn bench_fft_process_1024_f64(bencher: &mut test::Bencher) {
bench_fft_process!(bencher, 1024, f64);
fn bench_fft_process_1024_f64(c: &mut Criterion) {
bench_fft_process!(c, 1024, f64);
}

criterion_group!(
benches_fft_process,
bench_fft_process_1024_f32,
bench_fft_process_1024_f64
);

macro_rules! bench_stft_compute {
($bencher:expr, $window_size:expr, $float:ty) => {{
let mut stft = STFT::<$float>::new(WindowType::Hanning, $window_size, 0);
let input = std::iter::repeat(1.).take($window_size).collect::<Vec<$float>>();
let mut output = std::iter::repeat(0.).take(stft.output_size()).collect::<Vec<$float>>();
($c:expr, $window_size:expr, $float:ty) => {{
let step_size: usize = 512;
let mut stft = STFT::<$float>::new(WindowType::Hanning, $window_size, step_size);
let input = std::iter::repeat(1.)
.take($window_size)
.collect::<Vec<$float>>();
let mut output = std::iter::repeat(0.)
.take(stft.output_size())
.collect::<Vec<$float>>();
stft.append_samples(&input[..]);
$bencher.iter(|| {
stft.compute_column(&mut output[..])
});
}}
$c.bench_function(
concat!(
"bench_stft_compute_",
stringify!($window_size),
"_",
stringify!($float)
),
|b| b.iter(|| stft.compute_column(&mut output[..])),
);
}};
}

#[bench]
fn bench_stft_compute_1024_f32(bencher: &mut test::Bencher) {
bench_stft_compute!(bencher, 1024, f32);
fn bench_stft_compute_1024_f32(c: &mut Criterion) {
bench_stft_compute!(c, 1024, f32);
}

#[bench]
fn bench_stft_compute_1024_f64(bencher: &mut test::Bencher) {
bench_stft_compute!(bencher, 1024, f64);
fn bench_stft_compute_1024_f64(c: &mut Criterion) {
bench_stft_compute!(c, 1024, f64);
}

criterion_group!(
benches_stft_compute,
bench_stft_compute_1024_f32,
bench_stft_compute_1024_f64
);

macro_rules! bench_stft_audio {
($bencher:expr, $seconds:expr, $float:ty) => {{
($c:expr, $seconds:expr, $float:ty) => {{
// let's generate some fake audio
let sample_rate: usize = 44100;
let seconds: usize = $seconds;
let sample_count = sample_rate * seconds;
let all_samples = (0..sample_count).map(|x| x as $float).collect::<Vec<$float>>();
$bencher.iter(|| {
// let's initialize our short-time fourier transform
let window_type: WindowType = WindowType::Hanning;
let window_size: usize = 1024;
let step_size: usize = 512;
let mut stft = STFT::<$float>::new(window_type, window_size, step_size);
// we need a buffer to hold a computed column of the spectrogram
let mut spectrogram_column: Vec<$float> =
std::iter::repeat(0.).take(stft.output_size()).collect();
for some_samples in (&all_samples[..]).chunks(3000) {
stft.append_samples(some_samples);
while stft.contains_enough_to_compute() {
stft.compute_column(&mut spectrogram_column[..]);
stft.move_to_next_column();
}
}
});
}}
let all_samples = (0..sample_count)
.map(|x| x as $float)
.collect::<Vec<$float>>();
$c.bench_function(
concat!(
"bench_stft_audio_",
stringify!($windowsize),
"_",
stringify!($float)
),
|b| {
b.iter(|| {
// let's initialize our short-time fourier transform
let window_type: WindowType = WindowType::Hanning;
let window_size: usize = 1024;
let step_size: usize = 512;
let mut stft = STFT::<$float>::new(window_type, window_size, step_size);
// we need a buffer to hold a computed column of the spectrogram
let mut spectrogram_column: Vec<$float> =
std::iter::repeat(0.).take(stft.output_size()).collect();
for some_samples in (&all_samples[..]).chunks(3000) {
stft.append_samples(some_samples);
while stft.contains_enough_to_compute() {
stft.compute_column(&mut spectrogram_column[..]);
stft.move_to_next_column();
}
}
})
},
);
}};
}

#[bench]
fn bench_stft_10_seconds_audio_f32(bencher: &mut test::Bencher) {
bench_stft_audio!(bencher, 10, f32);
fn bench_stft_10_seconds_audio_f32(c: &mut Criterion) {
bench_stft_audio!(c, 10, f32);
}

#[bench]
fn bench_stft_10_seconds_audio_f64(bencher: &mut test::Bencher) {
bench_stft_audio!(bencher, 10, f64);
fn bench_stft_10_seconds_audio_f64(c: &mut Criterion) {
bench_stft_audio!(c, 10, f64);
}

criterion_group!(
benches_stft_audio,
bench_stft_10_seconds_audio_f32,
bench_stft_10_seconds_audio_f64
);

criterion_main!(
benches_fft_process,
benches_stft_compute,
benches_stft_audio
);
Loading