通过Rust编译时出现的错误来学习Rust
cannot assign twice to immutable variable x
不能复制两次不可变x
fn main() {
let x = 5; // solution: let mut x = 5;
println!("The value of x is {}", x);
x = 6;
println!("The value of x is {}", x);
}
consider giving guess
a type
尝试给guess
类型
let guess = "32".trim().parse().expect("Not a number!");
/// solution: let guess:i32 = "32".trim().parse().expect("Not a number!");
index out of bounds: the length is 2 but the index is 2
越界
fn main() {
let elements = [1, 2];
let index = 2;
println!("The value of elements is {}", elements[index]);
// review
let value:i8;
let value:i32;
let value:i64;
let value:isize;
let value:u8;
let value:u32;
let value:u64;
let value:usize;
let value = 92_222;
let value = 0xfff;
let value = 0o77;
let value = 0b1111_0000;
let value = b'A';
let value: f64 = 2.0;
let value: f32 = 3.0;
let value:bool = true;
let value:char = 'Z';
let value: (i32, bool) = (1, true);
let value1 = value.0;
let value2 = value.1;
let (value, valueB) = value;
let value:[i32; 3] = [1, 2, 3];
let value = [3; 3]; // [3, 3, 3]
let value1 = value[0];
}
expected expression, found statement (let
)
期望是表达式,但发现是语句
let valueA = (let valueB = 6);
mismatched types
类型不匹配
fn main() {
let x = plus_value(5);
println!("The value of x {}", x);
}
fn plus_value(value: i32) -> i32 {
value + 5;
}
/// 错误如下
fn plus_value(value: i32) -> i32 {
---------- ^^^ expected `i32`, found `()` 期望是 i32, 但是发现是空元组
|
implicitly returns `()` as its body has no tail or `return` expression
value + 5;
- help: consider removing this semicolon 帮助: 建议是移除分号
expected bool
, found integer
fn main() {
let number = 3;
if number { // solution: if number == 3 {
println!("continue was true");
}
else {
println!("continue was false");
}
}
if
and else
have incompatible types
fn main() {
let number = 3;
if number == 3 {
println!("continue was true");
}
else if number == 2 {
println!("continue was false");
}
let value = if number == 3 {
"The number is 3"
}
else {
5 // solution: "5"
};
}
Loop
fn main() {
let mut couter = 0;
let result = loop {
couter += 1;
if couter == 10 {
break couter * 2;
}
};
println!("result: {}", result);
while couter > 0 {
println!("couter: {}", couter);
couter -= 1;
}
let elements = [1, 2];
for element in elements.iter() {
println!("element: {}", element);
}
for number in (0..4).rev() {
println!("number: {}", number);
}
}
borrow of moved value: xxx
// error
let string1 = String::from("Hello");
------- move occurs because `string1` has type `String`, which does not implement the `Copy` trait
发生移动,是因为类型String不具有Copy特性
let string2 = string1;
------- value moved here
println!("string1 {}", string1);
^^^^^^^ value borrowed here after move
value移动后这里又再次使用
cannot borrow s
as mutable more than once at a time
fn main() {
let mut s = String::from("Hello");
push_str(&mut s);
// println!("{}", s);
let r1 = &mut s; /// 一次声明只能一次可变引用
let r2 = &mut s;
println!("r1 {}", r1);
{
let r1 = &mut s;
println!("r1 {}", r1);
}
{
let r2 = &mut s;
println!("r2 {}", r2);
}
}
fn push_str(s: &mut String) {
s.push_str(" World!");
}
cannot borrow s
as mutable because it is also borrowed as immutable
fn main() {
let mut s = String::from("Hello");
let r1 = &s;
let r2 = &s;
let r3 = &mut s;
println!("r1 {}", r1);
}
expected named lifetime parameter
fn main() {
let Hello = dangle();
}
// 悬垂引用
fn dangle() -> &String {
let value = String::from("Hello");
&value
}
cannot borrow s
as mutable because it is also borrowed as immutable
fn main() {
let mut s = String::from("Hello World!");
let world = first_word(&s);
s.clear();
println!("s {} world {}", s, world);
}
fn first_word(s: &String) -> &str {
let bytes = s.as_bytes();
for (i, &item) in bytes.iter().enumerate() {
if item == b' ' {
return &s[0..i]
}
}
return &s[..]
}
Struct
fn main() {
let user1 = User {
username: String::from("someone"),
email: String::from("someone@qq.com"),
};
let user2 = User {
username: user1.username,
..user1
};
}
fn build_user(username: String, email: String,) -> User {
return User {
username, email,
};
}
struct User {
username: String,
email: String,
}
#[derive(Debug)]
struct Rectangle {
width: u32,
height: u32,
}
impl Rectangle {
fn area(&self) -> u32 {
self.width * self.height
}
fn square(size: u32) -> Rectangle {
Rectangle { width: size, height: size}
}
}
impl Rectangle {
fn can_hold(&self, other: &Rectangle) -> bool {
self.width == other.width && self.height == other.height
}
}
fn main() {
let rect = Rectangle { width: 30, height: 30 };
println!("rect {:?} area {:?}", rect, rect.area());
}
struct
enum IpAddrKind {
V4,
V6,
}
struct IpAddr {
kind: IpAddrKind,
address: String,
}
fn main() {
let home = IpAddr {
kind: IpAddrKind::V4,
address: String::from("127.0.0.1"),
};
let loopback = IpAddr {
kind: IpAddrKind::V6,
address: String::from("::1"),
};
}
Enum
enum IpAddr {
V4(String),
V6(String),
}
let home = IpAddr::V4(String::from("127.0.0.1"));
let loopback = IpAddr::V6(String::from("::1"));
enum Message {
Quit,
Move { x: i32, y: i32 },
Write(String),
ChangeColor(i32, i32, i32),
}
struct QuitMessage; // unit struct
struct MoveMessage {
x: i32,
y: i32,
}
struct WriteMessage(String); // tuple struct
struct ChangeColorMessage(i32, i32, i32); // tuple struct
impl Message {
fn call(&self) {
// method body would be defined here
}
}
let m = Message::Write(String::from("hello"));
m.call();
non-exhaustive patterns: &None
not covered
fn plus_one(x: &Option<i32>) -> Option<i32> {
match x {
Some(i) => Some(i + 1),
}
}
fn main() {
let a: i32 = 1;
let b: Option<i32> = Some(5);
//let c = a + b; /// 错误
//println!("{}", c);
plus_one(&b);
}
If let
fn main() {
let some_u8_value = Some(3);
match some_u8_value {
Some(3) => println!("Three"),
_ => ()
}
if let Some(4) = some_u8_value {
println!("Three!");
}else {
println!("No match!");
}
}
通过Rust编译时出现的错误来学习Rust
cannot assign twice to immutable variable x
不能复制两次不可变x
fn main() {
let x = 5; // solution: let mut x = 5;
println!("The value of x is {}", x);
x = 6;
println!("The value of x is {}", x);
}
consider giving guess
a type
尝试给guess
类型
let guess = "32".trim().parse().expect("Not a number!");
/// solution: let guess:i32 = "32".trim().parse().expect("Not a number!");
index out of bounds: the length is 2 but the index is 2
越界
fn main() {
let elements = [1, 2];
let index = 2;
println!("The value of elements is {}", elements[index]);
// review
let value:i8;
let value:i32;
let value:i64;
let value:isize;
let value:u8;
let value:u32;
let value:u64;
let value:usize;
let value = 92_222;
let value = 0xfff;
let value = 0o77;
let value = 0b1111_0000;
let value = b'A';
let value: f64 = 2.0;
let value: f32 = 3.0;
let value:bool = true;
let value:char = 'Z';
let value: (i32, bool) = (1, true);
let value1 = value.0;
let value2 = value.1;
let (value, valueB) = value;
let value:[i32; 3] = [1, 2, 3];
let value = [3; 3]; // [3, 3, 3]
let value1 = value[0];
}
expected expression, found statement (let
)
期望是表达式,但发现是语句
let valueA = (let valueB = 6);
mismatched types
类型不匹配
fn main() {
let x = plus_value(5);
println!("The value of x {}", x);
}
fn plus_value(value: i32) -> i32 {
value + 5;
}
/// 错误如下
fn plus_value(value: i32) -> i32 {
---------- ^^^ expected `i32`, found `()` 期望是 i32, 但是发现是空元组
|
implicitly returns `()` as its body has no tail or `return` expression
value + 5;
- help: consider removing this semicolon 帮助: 建议是移除分号
expected bool
, found integer
fn main() {
let number = 3;
if number { // solution: if number == 3 {
println!("continue was true");
}
else {
println!("continue was false");
}
}
if
and else
have incompatible types
fn main() {
let number = 3;
if number == 3 {
println!("continue was true");
}
else if number == 2 {
println!("continue was false");
}
let value = if number == 3 {
"The number is 3"
}
else {
5 // solution: "5"
};
}
Loop
fn main() {
let mut couter = 0;
let result = loop {
couter += 1;
if couter == 10 {
break couter * 2;
}
};
println!("result: {}", result);
while couter > 0 {
println!("couter: {}", couter);
couter -= 1;
}
let elements = [1, 2];
for element in elements.iter() {
println!("element: {}", element);
}
for number in (0..4).rev() {
println!("number: {}", number);
}
}
borrow of moved value: xxx
// error
let string1 = String::from("Hello");
------- move occurs because `string1` has type `String`, which does not implement the `Copy` trait
发生移动,是因为类型String不具有Copy特性
let string2 = string1;
------- value moved here
println!("string1 {}", string1);
^^^^^^^ value borrowed here after move
value移动后这里又再次使用
cannot borrow s
as mutable more than once at a time
fn main() {
let mut s = String::from("Hello");
push_str(&mut s);
// println!("{}", s);
let r1 = &mut s; /// 一次声明只能一次可变引用
let r2 = &mut s;
println!("r1 {}", r1);
{
let r1 = &mut s;
println!("r1 {}", r1);
}
{
let r2 = &mut s;
println!("r2 {}", r2);
}
}
fn push_str(s: &mut String) {
s.push_str(" World!");
}
cannot borrow s
as mutable because it is also borrowed as immutable
fn main() {
let mut s = String::from("Hello");
let r1 = &s;
let r2 = &s;
let r3 = &mut s;
println!("r1 {}", r1);
}
expected named lifetime parameter
fn main() {
let Hello = dangle();
}
// 悬垂引用
fn dangle() -> &String {
let value = String::from("Hello");
&value
}
cannot borrow s
as mutable because it is also borrowed as immutable
fn main() {
let mut s = String::from("Hello World!");
let world = first_word(&s);
s.clear();
println!("s {} world {}", s, world);
}
fn first_word(s: &String) -> &str {
let bytes = s.as_bytes();
for (i, &item) in bytes.iter().enumerate() {
if item == b' ' {
return &s[0..i]
}
}
return &s[..]
}
Struct
fn main() {
let user1 = User {
username: String::from("someone"),
email: String::from("someone@qq.com"),
};
let user2 = User {
username: user1.username,
..user1
};
}
fn build_user(username: String, email: String,) -> User {
return User {
username, email,
};
}
struct User {
username: String,
email: String,
}
#[derive(Debug)]
struct Rectangle {
width: u32,
height: u32,
}
impl Rectangle {
fn area(&self) -> u32 {
self.width * self.height
}
fn square(size: u32) -> Rectangle {
Rectangle { width: size, height: size}
}
}
impl Rectangle {
fn can_hold(&self, other: &Rectangle) -> bool {
self.width == other.width && self.height == other.height
}
}
fn main() {
let rect = Rectangle { width: 30, height: 30 };
println!("rect {:?} area {:?}", rect, rect.area());
}
struct
enum IpAddrKind {
V4,
V6,
}
struct IpAddr {
kind: IpAddrKind,
address: String,
}
fn main() {
let home = IpAddr {
kind: IpAddrKind::V4,
address: String::from("127.0.0.1"),
};
let loopback = IpAddr {
kind: IpAddrKind::V6,
address: String::from("::1"),
};
}
Enum
enum IpAddr {
V4(String),
V6(String),
}
let home = IpAddr::V4(String::from("127.0.0.1"));
let loopback = IpAddr::V6(String::from("::1"));
enum Message {
Quit,
Move { x: i32, y: i32 },
Write(String),
ChangeColor(i32, i32, i32),
}
struct QuitMessage; // unit struct
struct MoveMessage {
x: i32,
y: i32,
}
struct WriteMessage(String); // tuple struct
struct ChangeColorMessage(i32, i32, i32); // tuple struct
impl Message {
fn call(&self) {
// method body would be defined here
}
}
let m = Message::Write(String::from("hello"));
m.call();
non-exhaustive patterns: &None
not covered
fn plus_one(x: &Option<i32>) -> Option<i32> {
match x {
Some(i) => Some(i + 1),
}
}
fn main() {
let a: i32 = 1;
let b: Option<i32> = Some(5);
//let c = a + b; /// 错误
//println!("{}", c);
plus_one(&b);
}
If let
fn main() {
let some_u8_value = Some(3);
match some_u8_value {
Some(3) => println!("Three"),
_ => ()
}
if let Some(4) = some_u8_value {
println!("Three!");
}else {
println!("No match!");
}
}