Rust 我怎样才能抓住人造丝的恐慌';是“par_iter()”?
我试图从Rust 我怎样才能抓住人造丝的恐慌';是“par_iter()”?,rust,panic,rayon,Rust,Panic,Rayon,我试图从par_iter()内部捕捉恐慌,并在par_iter块之后继续我所拥有的 如果我有这个,我会正确地得到所有信息,不会出现恐慌: let dog: Dog = Dog { name: "Dog", vector: vec![1, 2, 3, 4, 5], }; let cat: Cat = Cat { name: "Cat", vector: vec![1, 2, 3], }; let pig: Pig = Pig { name: "Pig",
par_iter()
内部捕捉恐慌,并在par_iter
块之后继续我所拥有的
如果我有这个,我会正确地得到所有信息,不会出现恐慌:
let dog: Dog = Dog {
name: "Dog",
vector: vec![1, 2, 3, 4, 5],
};
let cat: Cat = Cat {
name: "Cat",
vector: vec![1, 2, 3],
};
let pig: Pig = Pig {
name: "Pig",
vector: vec![1, 2, 3, 4, 5],
};
let mut v: Vec<Box<dyn Animal>> = Vec::new();
v.push(Box::new(cat));
v.push(Box::new(dog));
v.push(Box::new(pig));
let total = v
.par_iter()
.map(|x| {
println!("{} vector[1] is {:?}", &x.name(), &x.vector()[1]);
x.vector()[1].clone()
})
.collect::<Vec<(i32)>>();
let sum: i32 = total.iter().sum();
println!("sum: {}", sum);
当我试图访问一个超过向量长度的索引时,我仍然会打印我所有的内容,包括panic,但不会得到和:
let total = v
.par_iter()
.map(|x| {
println!("{} vector[4] is {:?}", &x.name(), &x.vector()[4]);
x.vector()[4].clone()
})
.collect::<Vec<(i32)>>();
let sum: i32 = total.iter().sum();
println!("sum: {}", sum);
它不起作用,甚至没有使用:
警告:未使用的变量:`err`
-->src/main.rs:52:31
|
52 |让恐慌|处理程序=移动|错误:框|{
^ ^ ^帮助:考虑前缀与下划线:'Eyrr '
我真正的问题不是超出向量的界限,而是在我不知道它是否会恐慌的情况下从par_iter
捕捉恐慌。我的目标是收集结果并继续使用没有恐慌的东西。尝试使用get
(它返回一些(元素)
如果索引4处有一个元素,无
否则):
let total=v.par_iter().map(| x |{
println!(“{}向量[4]是{:?}”,&x.name(),&x.vector().get(4));
x、 vector().get(4.map)(|x | x.clone())
})收集::();
然后,total
将包含一些(n)
,其中相应的元素存在,而则不存在。我的问题是使用::std::panic::catch\u unwind()
:
use::rayon::prelude::*;
动物特征:同步+发送{
fn向量(self:&“self)->Vec;
fn名称(self:&“self)->字符串;
}
结构猫{
名称:&'static str,
向量:向量,
}
猫科动物{
fn向量(self:&“self)->Vec{
self.vector.clone()
}
fn名称(self:&“self)->字符串{
self.name.to_string()
}
}
结构狗{
名称:&'static str,
向量:向量,
}
为狗准备的动物{
fn向量(self:&“self)->Vec{
self.vector.clone()
}
fn名称(self:&“self)->字符串{
self.name.to_string()
}
}
结构清管器{
名称:&'static str,
向量:向量,
}
猪用动物{
fn向量(self:&“self)->Vec{
self.vector.clone()
}
fn名称(self:&“self)->字符串{
self.name.to_string()
}
}
fn main(){
::人造丝::ThreadPoolBuilder::新建()
.num_线程(2)
//.panic_handler(move | |:Box | println!(“你好”))
.build_global()
.unwrap();
匹配::std::恐慌::捕捉|放松(移动| |{
让狗吃吧{
名字:“狗”,
向量:向量![1,2,3,4,5],
};
让猫:猫=猫{
名称:“猫”,
向量:向量![1,2,3],
};
让猪:猪=猪{
名称:“猪”,
向量:向量![1,2,3,4,5],
};
让v:Vec=Vec![Box::new(猫),Box::new(狗),Box::new(猪)];
让总数=v
.par_iter()
.map(|x|){
设vector_4=x.vector()[4].clone();
println!(“{}向量[4]是{:?}”,&x.name(),向量_4);
向量_4
})
收集::();
让sum:i32=total.iter().sum();
println!(“和:{}”,和);
}) {
好(())=>(),
错误(Err)=>{
让err_msg=match(err.downcast_ref(),err.downcast_ref::()){
(部分(&s),)=>s,
(部分)=>&**,
_ => "",
};
eprintln!(“人造丝恐慌:{}”,err_msg);
}
}
println!(“始终达到此代码”);
}
这不是在Rust中进行错误处理的方法。在为向量编制索引之前检查边界,或者使用Vec::get
顺便说一句,您不需要显式显示大多数类型,如果您只需要Sumfrence Boiethios,您也不需要收集结果谢谢,我正在收集结果,因为这是我正在做的工作的一部分,我还需要嗯,我只是简化了代码,因为我需要结果本身。我之前也不能检查,因为我有许多任务和表,它们中的每一个都可能会出现恐慌,我的目标是从所有不会恐慌的任务中收集结果。谢谢!谢谢!但是如果我不知道我在par_iter()中运行的许多任务中的哪一个
陷入恐慌(不正确的列、展开等)如何使恐慌变成无
?我将使用产生结果的任务(除非部分代码恐慌)。是否有可能在par_iter
中捕捉到任何恐慌并继续前进?谢谢!Maria,你能将此评论编辑为解决方案代码的一部分吗?然后你可以接受它作为答案。
let panic_handler = move |err: Box<dyn Any + Send>| {
println!("hello");
};
rayon::ThreadPoolBuilder::new()
.num_threads(2)
.panic_handler(panic_handler)
.build_global()
.unwrap();
let total = v.par_iter().map(|x| {
println!("{} vector[4] is {:?}", &x.name(), &x.vector().get(4));
x.vector().get(4).map(|x| x.clone())
}).collect::<Vec<Option<i32>>>();
use ::rayon::prelude::*;
trait Animal: Sync + Send {
fn vector(self: &'_ Self) -> Vec<i32>;
fn name(self: &'_ Self) -> String;
}
struct Cat {
name: &'static str,
vector: Vec<i32>,
}
impl Animal for Cat {
fn vector(self: &'_ Self) -> Vec<i32> {
self.vector.clone()
}
fn name(self: &'_ Self) -> String {
self.name.to_string()
}
}
struct Dog {
name: &'static str,
vector: Vec<i32>,
}
impl Animal for Dog {
fn vector(self: &'_ Self) -> Vec<i32> {
self.vector.clone()
}
fn name(self: &'_ Self) -> String {
self.name.to_string()
}
}
struct Pig {
name: &'static str,
vector: Vec<i32>,
}
impl Animal for Pig {
fn vector(self: &'_ Self) -> Vec<i32> {
self.vector.clone()
}
fn name(self: &'_ Self) -> String {
self.name.to_string()
}
}
fn main() {
::rayon::ThreadPoolBuilder::new()
.num_threads(2)
// .panic_handler(move |_: Box<dyn Any + Send>| println!("hello"))
.build_global()
.unwrap();
match ::std::panic::catch_unwind(move || {
let dog: Dog = Dog {
name: "Dog",
vector: vec![1, 2, 3, 4, 5],
};
let cat: Cat = Cat {
name: "Cat",
vector: vec![1, 2, 3],
};
let pig: Pig = Pig {
name: "Pig",
vector: vec![1, 2, 3, 4, 5],
};
let v: Vec<Box<dyn Animal>> = vec![Box::new(cat), Box::new(dog), Box::new(pig)];
let total = v
.par_iter()
.map(|x| {
let vector_4 = x.vector()[4].clone();
println!("{} vector[4] is {:?}", &x.name(), vector_4);
vector_4
})
.collect::<Vec<(i32)>>();
let sum: i32 = total.iter().sum();
println!("sum: {}", sum);
}) {
Ok(()) => (),
Err(err) => {
let err_msg = match (err.downcast_ref(), err.downcast_ref::<String>()) {
(Some(&s), _) => s,
(_, Some(s)) => &**s,
_ => "<No panic message>",
};
eprintln!("Rayon panicked: {}", err_msg);
}
}
println!("This code is always reached");
}