使用 for 循环显示矩阵时类型不匹配

Mismatched types when displaying a matrix with a for loop

受post中evilone提供的代码启发。为了显示矩阵,我编写了如下代码:

use std::{ops, fmt};

#[derive(PartialEq, Debug)]
pub struct Matrix<T> {
    data: Vec<T>,
    row: usize,
    col: usize,
}

impl<T: Copy> Matrix<T> {       
    pub fn new(row: usize, col: usize, values: &[T]) -> Matrix<T> {
        Matrix {
            data: values.to_vec(), 
            row: row,
            col: col,
        }
    }
}    

//// Display
impl<T: fmt::Display> fmt::Display for Matrix<T> {

    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        let n_row = self.row;
        let n_col = self.col;
        let data = self.data;

        for i in 0.. n_row {
            let mut each_row = String::new(); 

            for j in 0.. n_col {
                let idx = i * n_col + j;  
                let each_element = data[idx];
                each_row.push_str(&each_element.to_string());
                each_row.push_str(" ");  // seperated by space 
            }
            write!(f, "{}", each_row)   
        }
    }
}    

fn main() {
    let x = Matrix::new(2, 3, &[-6, -5, 0, 1, 2, 3]);
    println!("{}", x);

}

我收到错误:

rustc 1.13.0 (2c6933acc 2016-11-07)
error[E0308]: mismatched types
  --> <anon>:40:13
   |
40 |             write!(f, "{}", each_row)   
   |             ^^^^^^^^^^^^^^^^^^^^^^^^^ expected (), found enum `std::result::Result`
   |
   = note: expected type `()`
   = note:    found type `std::result::Result<(), std::fmt::Error>`
   = note: this error originates in a macro outside of the current crate

error[E0308]: mismatched types
  --> <anon>:31:9
   |
31 |         for i in 0.. n_row {
   |         ^ expected enum `std::result::Result`, found ()
   |
   = note: expected type `std::result::Result<(), std::fmt::Error>`
   = note:    found type `()`

1) 我不明白为什么会得到 expected (), found enum `std::result::Result`

2) 对于第二个错误,我认为是第40行实现失败导致的。所以如果修复第40行,就不会再有问题了。

有什么解决这个问题的建议吗?

这是针对此问题的 MRE

fn foo() -> u8 {
    for i in 0..1u8 {
        i
    }
}

它会产生这些熟悉的错误:

error[E0308]: mismatched types
 --> src/lib.rs:3:9
  |
3 |         i
  |         ^ expected `()`, found `u8`
  |
help: you might have meant to return this value
  |
3 |         return i;
  |         ++++++  +

error[E0308]: mismatched types
 --> src/lib.rs:2:5
  |
1 |   fn foo() -> u8 {
  |               -- expected `u8` because of return type
2 | /     for i in 0..1u8 {
3 | |         i
4 | |     }
  | |_____^ expected `u8`, found `()`

现在的问题是“for 循环的计算结果是什么类型和值?” (提示:编译器消息实际上会告诉您阅读方式是否正确)

我们知道函数必须return一个u8,但是编译器告诉我们我们实际上是return一个() — 这是第二个错误。这意味着 for 循环的计算结果为 ()!由于 for 循环的计算结果为 (),因此 for 循环块的计算结果可能会发生什么变化?你可以猜到,答案是块不能 return一个值!

想想这个例子:

fn foo() -> u8 {
    for i in 0..0u8 {
        //
    }
}

这个return会是什么?可能没什么好东西。


从我们的MRE回到原来的问题,你需要在循环结束后显式return内部失败和显式return成功:

for /* ... */ {
    // ...

    write!(f, "{}", each_row)?;
}

Ok(())

这为代码中的其他错误打开了大门,但我相信您有能力解决这些错误!