I want to iterate over vec to find the best element. In c++ I will save reference to first element and will compare with the next element and if the next is better I will point the refference to next element and so on. How do I do this in rust
Here is link to rust playground with example. I want to remove the line with "// !!! I want to remove that line"
The problem is that when I unpack optional to read the data, the values are consumed and I need to reinitiliaze it again
And here is my original code :
fn find_intersection<'a>(&self, ray : &Ray, scene : &'a Scene) -> Option<(&'a Box<dyn SceneElement>, IntersectionInfo)> {
let mut result : Option<(&Box<dyn SceneElement>, IntersectionInfo)> = None;
for element in &scene.elements {
if let Some(info) = element.geometry().intersect(&ray) {
let found_new = if let Some((node, old_info)) = result {
let t = info.distance < old_info.distance;
result = Some((node, old_info));
t
} else {true};
if found_new {
result = Some((element, info));
}
}
}
result
}
Thanks a lot for your answer. I'm still not convinced that iterators and combinators lead to better or at least same performance compared to carefully designed for cycle. So far it's look like wishful thinking. So far I don't have big enough application to test it. Do you have such experience ? What is your opinion on that topic ?
Despite being less direct / more abstract, the std iterators are pretty optimizied, and there are also combinators like chunks_exact that are aimed at auto-vectorization depending on your circumstance. So iterators can actually improve performance. That said, it's no guarantee; hand-tuned code or just incidentally non-iterator-using code can still be faster.
Therefore, my opinions are
either way might be faster, so
write it whichever way is most comfortable to you, then
only optimize when you know it's a relevant bottleneck, and also
don't assume it is a bottleneck or assume which approach is faster; measure instead.
What leads you to believe this? Do you have data to back it up? If not, then you should just write the code the more idiomatic, clearer way, and not worry about such (usually trivial) performance differences.
Several people have explained to you in this thread how iterators work. If you don't believe them, feel free to, but that is not going to be the fault of the language.
It happens due to inlining. All of the iterator functions involved take functions as generic arguments, and every single closure generates a new unique type. Because of how generics works, this means that the actual iterator functions you are calling are only ever called from your find_intersection method. This makes it pretty much guaranteed that the compiler will inline them.
Once they're inlined into the function, it isn't very difficult for the compiler to optimize it into something like a handwritten loop.