I'm using Nalgebra's VectorN<f64, N> type in some single-threaded code which is working well. I'm now trying to multithread various parts of the algorithm, but have run into issues passing VectorNs into a thread::spawn call. For example, the following code fails to compile:
use std::thread;
use nalgebra::{VectorN, DefaultAllocator, DimName};
use nalgebra::allocator::Allocator;
struct Test<N>
where
N: DimName,
DefaultAllocator: Allocator<f64, N>,
{
pub field: VectorN<f64, N>,
}
impl<N> Test<N>
where
N: DimName,
DefaultAllocator: Allocator<f64, N>,
{
pub fn test(&self) {
let handle = thread::spawn(move || {
let thing = self.field;
let thing2 = thing * 2.0;
thing2
});
let res = handle.join().unwrap();
}
}
With this error:
error[E0277]: `<nalgebra::base::default_allocator::DefaultAllocator as nalgebra::base::allocator::Allocator<f64, N>>::Buffer` cannot be sent between threads safely
--> trajectories/src/path/mod.rs:34:22
|
34 | let handle = thread::spawn(move || {
| ^^^^^^^^^^^^^ `<nalgebra::base::default_allocator::DefaultAllocator as nalgebra::base::allocator::Allocator<f64, N>>::Buffer` cannot be sent between threads safely
|
= help: within `nalgebra::base::matrix::Matrix<f64, N, nalgebra::base::dimension::U1, <nalgebra::base::default_allocator::DefaultAllocator as nalgebra::base::allocator::Allocator<f64, N>>::Buffer>`, the trait `std::marker::Send` is not
implemented for `<nalgebra::base::default_allocator::DefaultAllocator as nalgebra::base::allocator::Allocator<f64, N>>::Buffer`
= note: required because it appears within the type `nalgebra::base::matrix::Matrix<f64, N, nalgebra::base::dimension::U1, <nalgebra::base::default_allocator::DefaultAllocator as nalgebra::base::allocator::Allocator<f64, N>>::Buffer>`
= note: required by `std::thread::spawn`
I've tried various definitions for N and DefaultAllocator in the where clauses but haven't got far. Various search engines have turned up nothing useful around this issue.
If I replace VectorN<f64, N> with VectorN<f64, U3> (or any other U* type from Nalgebra), the above error goes away. I've read the Nalgebra generic programming guide however that seems out of date and perhaps not what I need; I don't want complete genericity, just the ability to use VectorN with any size bound. What trait bounds do I need to put on my struct so I can pass field into a thread?