rust - Mismatched types when implementing a trait -


to learn rust, i'm building own matrix class. implementation of add trait follows:

impl<t: add> add matrix<t> {     type output = matrix<t>;      fn add(self, _rhs: matrix<t>) -> matrix<t>     {         assert!(self.rows == _rhs.rows && self.cols == _rhs.cols,                 "attempting add matrices of different sizes");          let mut res: matrix<t> = matrix::<t>{             rows: self.rows,             cols: self.cols,             data : vec::<t>::with_capacity(self.rows * self.cols),         };          in 0..self.rows*self.cols{             res.data.push(self.data[i] + _rhs.data[i]);         }         res    } } 

but following error

       compiling matrix v0.1.0 (file://~/soft/rust/projects/matrix) src/lib.rs:35:27: 35:54 error: mismatched types:  expected `t`,     found `<t core::ops::add>::output` (expected type parameter,     found associated type) [e0308] src/lib.rs:35             res.data.push(self.data[i] + _rhs.data[i]);                                         ^~~~~~~~~~~~~~~~~~~~~~~~~~~ 

going error report, guess need indicate somewhere else t implements add trait anywhere try either same error or parsing error.

my definition of matrix way is

pub struct matrix<t> {     pub rows: usize,     pub cols: usize,     pub data: vec<t>, } 

using t: add bound says 1 can write t + t, doesn't place restriction on type result that, in particular, may not t. you're relying on being t able return matrix<t>.

one approach require t: add<output = t>, t + t returns t:

impl<t: add<output = t>> add matrix<t> {     ... } 

another approach instead work whatever output t wants give: i.e. addition return matrix<t::output>:

impl<t: add> add matrix<t> {     type output = matrix<t::output>;      fn add(self, _rhs: matrix<t>) -> matrix<t::output>     {         assert!(self.rows == _rhs.rows && self.cols == _rhs.cols,                 "attempting add matrices of different sizes");          let mut res = matrix {             rows: self.rows,             cols: self.cols,             data : vec::with_capacity(self.rows * self.cols),         };          in 0..self.rows*self.cols{             res.data.push(self.data[i] + _rhs.data[i]);         }         res    } } 

however, both of these meet problem:

<anon>:23:27: 23:39 error: cannot move out of indexed content <anon>:23             res.data.push(self.data[i] + _rhs.data[i]);                                     ^~~~~~~~~~~~ <anon>:23:42: 23:54 error: cannot move out of indexed content <anon>:23             res.data.push(self.data[i] + _rhs.data[i]);                                                    ^~~~~~~~~~~~ 

add/the + operator takes ownership of arguments, , 1 cannot move ownership out of vector direct indexing (in general, compiler can't tell 1 won't try access moved-out index again, later, safety problem). fortunately, there's solution: vectors support moving-out iterator, , 1 can walk on self , _rhs moving out in lock-step:

for (a, b) in self.data.into_iter().zip(_rhs.data.into_iter()) {     res.data.push(a + b) } 

the a , b variables both of type t, i.e. ownership has moved.


minor note, 1 can "iteratorise" code more, writing:

fn add(self, _rhs: matrix<t>) -> matrix<t::output> {     assert!(self.rows == _rhs.rows && self.cols == _rhs.cols,             "attempting add matrices of different sizes");      let data = self.data.into_iter()          .zip(_rhs.data.into_iter())         .map(|(a,b)| + b)         .collect();     matrix {         rows: self.rows,         cols: self.cols,         data: data     } } 

Comments

Popular posts from this blog

php - failed to open stream: HTTP request failed! HTTP/1.0 400 Bad Request -

java - How to filter a backspace keyboard input -

java - Show Soft Keyboard when EditText Appears -