gpt4 book ai didi

rust - 如何将动态分配与以迭代器作为参数的方法一起使用?

转载 作者:行者123 更新时间:2023-12-03 11:38:47 25 4
gpt4 key购买 nike

我正在编写一个用于使用rust 的命令行应用程序,用于处理来自传感器的音频。我希望用户能够从多个选项中选择要应用的算法或过滤器。我希望使用动态调度来切换出一个在运行时实现我的过滤器特征的结构。但是,编译器不允许这样做,因为其中一种trait方法采用通用参数。
我如何实现相同的功能而又不会引起任何编译器麻烦?我知道一个简单的解决方案是将process方法的参数更改为数组或向量,但这是我的最后选择,因为我更喜欢采用Iterator或IntoIterator,因为它更通用,更适合我的具体需求。
这是一些演示问题的代码。

trait SensorFilter {
fn process(&self, sig: &mut impl Iterator<Item = f32>) -> Vec<f32>;
}

struct Alg1 {
mul: f32,
}

struct Alg2 {
add: f32,
}

impl SensorFilter for Alg1 {
fn process(&self, sig: &mut impl Iterator<Item = f32>) -> Vec<f32> {
sig.map(|x| x * self.mul).collect()
}
}

impl SensorFilter for Alg2 {
fn process(&self, sig: &mut impl Iterator<Item = f32>) -> Vec<f32> {
sig.map(|x| x * self.add).collect()
}
}

enum AlgChoice {
Alg1,
Alg2
}

fn main() {
let choice = AlgChoice::Alg1; // user chooses via command-line.
let mut sig = vec![0.,1.,2.,3.,4.,5.,6.].into_iter(); // iterator gets data from sensor.

// This doesn't work, because my trait cannot be made into an object.
let alg: &dyn SensorFilter = match choice {
AlgChoice::Alg1 => Alg1{mul:0.3},
_ => Alg2{add:1.2},
};

let result = alg.process(&mut sig);
println!("{:?}",result);
}

谢谢 :)

最佳答案

这里的技巧是将您的泛型函数参数更改为泛型特征参数:

// Make the generic param into a type argument w/ constraints
trait SensorFilter<I> where I: Iterator<Item = f32> {
fn process(&self, sig: &mut I) -> Vec<f32>;
}

struct Alg1 {
mul: f32,
}

struct Alg2 {
add: f32,
}

// Implement trait for all I that match the iterator constraint
impl<I: Iterator<Item = f32>> SensorFilter<I> for Alg1 {
fn process(&self, sig: &mut I) -> Vec<f32> {
sig.map(|x| x * self.mul).collect()
}
}

impl<I: Iterator<Item = f32>> SensorFilter<I> for Alg2 {
fn process(&self, sig: &mut I) -> Vec<f32> {
sig.map(|x| x * self.add).collect()
}
}

enum AlgChoice {
Alg1,
Alg2
}

fn main() {
let choice = AlgChoice::Alg1; // user chooses via command-line.
let mut sig = vec![0.,1.,2.,3.,4.,5.,6.].into_iter(); // iterator gets data from sensor.

// Specify the type argument of your trait.
let alg: &dyn SensorFilter<std::vec::IntoIter<f32>> = match choice {
AlgChoice::Alg1 => &Alg1{mul:0.3},
_ => &Alg2{add:1.2},
};

let result = alg.process(&mut sig);
println!("{:?}",result);
}

关于rust - 如何将动态分配与以迭代器作为参数的方法一起使用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/64377501/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com