【发布时间】:2020-03-10 20:21:56
【问题描述】:
我正在组装一个音频 dsp,并且我正在寻找一种更“rustacean”的方式来实现以下内容:
pub struct TransformOptions<SourceType> {
transform : Option<Box<dyn Fn(&mut [SourceType; FFT_SIZE], &mut [SourceType; FFT_SIZE])>>,
filter : Option<Box<dyn Fn(&mut [SourceType; FFT_SIZE], [SourceType; FFT_SIZE])>>,
inverse_transform : Option<Box<dyn Fn(&mut [SourceType; FFT_SIZE], &mut [SourceType; FFT_SIZE])>>
//should try anddo this in an array
//options : [Option; NUM_TRANSFORM_OPTIONS],
}
impl<SourceType : Default> TransformOptions<SourceType> {
fn cycle_through(&self, input : [SourceType; FFT_SIZE])->[SourceType; FFT_SIZE] {
//let input : [T ; FFT_SIZE] = arr![T; FFT_SIZE];
//This represents the amplitude of the signal represented as the distance from the origin on a unit circle
//Here we transform the signal from the time domain to the frequency domain.
//Note that humans can only hear sound with a frequency between 20Hz and 20_000Hz
// fft.process(&mut time_ring_buffer[time_index..time_index + fft_size], &mut complex_freq_buffer[..]);
if let Some(_) = self.transform{
let transform_func = self.transform.unwrap();
let output = input.clone();
transform_func(&input, &output);
input = output;
}
//the analytic array acts as a filter, removing the negative and dc portions
//of the signal as well as filtering out the nyquist portion of the signal
//Also applies the hamming window here
// By applying the inverse fourier transform we transform the signal from the frequency domain back into the
if let Some(_) = self.filter {
let filter_func = self.filter.unwrap();
/*
this is roughly how it should go down
| input, coefficient | {
for input_idx in index.ter() {
input_idx = input_idx * coeffcient[input_idx.index];
}
}
*/
input = filter_func(&input);
}
// By applying the inverse fourier transform we transform the signal from the frequency domain back into the
// time domain. However now this signal can be represented as a series of points on a unit circle.
// ifft.process(&mut complex_freq_buffer[..], &mut complex_analytic_buffer[..]);
if let Some(_) = self.inverse_transform {
let transform_func = self.inverse_transform.unwrap();
let output = input.clone();
transform_func(&input, &output);
input = output;
}
input
}
}
基本上我想做的是拥有某种特征,它收集一些子特征并检查它们是否在这个结构上实现。如果是,则调用它们各自的顶级函数并适当地传递数据。我不确定是否有比目前更好的方法来实现这一点。
编辑:像这样的东西就是我正在拍摄的 是否有可能/建议做这样的事情?
trait Transform {
fn transform(&self, &mut [SourceType; FFT_SIZE], &mut [SourceType; FFT_SIZE]) {
// default implementation does nothing
}
}
trait InverseTransform {
fn filter(&self, &mut [SourceType; FFT_SIZE], [SourceType; FFT_SIZE]) {
// default implementation does nothing
}
}
trait InverseTransform {
fn inverse_transform(&self, &mut [SourceType; FFT_SIZE], &mut [SourceType; FFT_SIZE]) {
// default implementation does nothing
}
}
trait TransformOptions {
//Check for and use the above traits in here somehow. Leaving room for implementation
}
【问题讨论】:
标签: struct rust signal-processing traits