rust的struct
定义和实例化struct
使用struct关键字,并对整个struct命名。
在花括号内,对所有字段(Field)定义名称和类型。
创建struct实例:为每个字段指定具体值,无需按声明顺序进行指定。
struct User {
name: String,
id: u64,
is_act: bool,
}
fn main() {
let u1 = User {
name: String::from("test"),
is_act: true,
id: 12,
}
}
操作字段
使用点标记法操作字段,一旦struct实例是可变的,那么实例中所有字段都是可变的。
struct User {
name: String,
id: u64,
is_act: bool,
}
fn main() {
let mut u1 = User {
name: String::from("test"),
is_act: true,
id: 12,
}
u1.name = String::from("t2");
}
struct作为函数的返回值
struct User {
name: String,
id: u64,
is_act: bool,
}
fn return_struct(nm: String, is_act: bool) -> User {
User {
name: nm,
is_act: is_act,
id: 0,
}
}
当字段名与字段值对应变量名相同时,可使用字段初始化简写的方式。
struct User {
name: String,
id: u64,
is_act: bool,
}
fn return_struct(name: String, is_act: bool) -> User {
User {
name,
is_act,
id: 0,
}
}
struct的更新语法
当基于某个struct实例创建一个新实例时,可用更新语法:
fn main() {
let mut u1 = User {
name: String::from("test"),
is_act: true,
id: 12,
}
u1.name = String::from("t2");
let u2 = User {
name: String::from("test2"),
..u1 // 更新语法,表示剩余字段用u1的值来填充
}
}
tuple struct
tuple struct:定义类似于tuple的struct,tuple struct整体有个命名,但里边元素没有名称。
适应:想给整个tuple起名,使其不同于其他tuple,且无需给每个元素命名。
定义tuple struct:使用struct关键字 名字(元素类型列表)
struct Color(i32, i32, i32);
struct P(i32, i32, i32);
let b = Color(0, 0, 0);
let s = P(0, 0, 0); // s和b是两个不同类型数据
可用模式匹配和点索引的方式访问字段。
Unit-Like struct(没有任何字段)
可定义没有任何字段的struct,叫Unit-Like struct(因为与(),单元类型类似).
适于需要在某个类型上实现某个trait,但没有需要存储的数据。
struct数据的所有权
struct User {
name: String,
id: u64,
is_act: bool,
}
这里字段使用了String而不是&str,该struct实例拥有其所有的数据,只要struct实例有效,其字段也有效。
struct里也可放引用,需使用生命周期的知识。
看个实践:
struct Rect {
w: u32,
l: u32,
}
fn main() {
let rect = (30, 40);
println!("{}", get_area(rect));
let rect_struct = Rect {
w: 30,
l: 40,
}
// 传入不可变的引用,传入后为不可变借用,不会改变变量的所有权,所有权依然归属于main函数
println!("{}", get_area_struct(&rect_struct));
}
fn get_area(rect: (u32, u32)) -> u32 { // 使用tuple实现
rect.0 * rect.1 // 无法区分谁是长和宽
}
fn get_area_struct(rect: &Rect) -> u32 { // 使用结构体的不可变的借用即可,无需获得所有权
rect.w * rect.l
}
rust的打印与调试信息
首先看下直接打印
struct Rect {
w: u32,
l: u32,
}
fn main() {
let rect = Rect {
w: 30,
l: 40,
};
// 传入不可变的引用,传入后为不可变借用,不会改变变量的所有权,所有权依然归属于main函数
println!("{}", get_area_struct(&rect));
println!("{}", rect);
/* 直接打印,编译报错信息(没有实现display):
error[E0277]: `Rect` doesn't implement `std::fmt::Display`
--> src\main.rs:114:20
|
114 | println!("{}", rect);
| ^^^^ `Rect` cannot be formatted with the default formatter
|
= help: the trait `std::fmt::Display` is not implemented for `Rect`
= note: in format strings you may be able to use `{:?}` (or {:#?} for pretty-print) instead
*/
}
fn get_area_struct(rect: &Rect) -> u32 { // 使用结构体的不可变的借用即可,无需获得所有权
rect.w * rect.l
}
注释中附带的编译报错信息,是指Rect结构体没有实现打印trait std::fmt::Display
,不清楚如何打印。其他基础类型能答应是因rust默认实现了这些类型的display trait,而自定义类型无默认实现。
但下一行提示可使用{:?}
(or {:#?} for pretty-print)来代替。
struct Rect {
w: u32,
l: u32,
}
fn main() {
let rect = Rect {
w: 30,
l: 40,
};
// 传入不可变的引用,传入后为不可变借用,不会改变变量的所有权,所有权依然归属于main函数
println!("{}", get_area_struct(&rect));
println!("{:?}", rect);
/* 加上{:?}后打印,编译报错信息(变成了没有实现debug):
error[E0277]: `Rect` doesn't implement `Debug`
--> src\main.rs:114:22
|
114 | println!("{:?}", rect);
| ^^^^ `Rect` cannot be formatted using `{:?}`
|
= help: the trait `Debug` is not implemented for `Rect`
= note: add `#[derive(Debug)]` to `Rect` or manually `impl Debug for Rect`
*/
}
fn get_area_struct(rect: &Rect) -> u32 { // 使用结构体的不可变的借用即可,无需获得所有权
rect.w * rect.l
}
错误信息变成了没有实现debug,debug和display一样,也是一种格式化的方法。下一行提示可加上#[derive(Debug)]
或者手动实现debug。这是因为rust默认包含了打印调试信息的功能,但需要显示添加,能直接打印。
#[derive(Debug)] // 需要显示加上打印调试信息
struct Rect {
w: u32,
l: u32,
}
fn main() {
let rect = Rect {
w: 30,
l: 40,
};
// 传入不可变的引用,传入后为不可变借用,不会改变变量的所有权,所有权依然归属于main函数
println!("{}", get_area_struct(&rect));
println!("{:?}", rect); // 一行打印
println!("\n{:#?}", rect); // 加上#后换行打印
}
fn get_area_struct(rect: &Rect) -> u32 { // 使用结构体的不可变的借用即可,无需获得所有权
rect.w * rect.l
}
/* 打印输出:
Rect { w: 30, l: 40 }
Rect {
w: 30,
l: 40,
}
*/
这是因为rust提供了很多默认的trait(已实现好的函数方法),可用于derive,#[derive(Debug)]中的derive是派生的意思,可利用现有trait,给自定义类型添加很多功能。#[derive(Debug)]整行的意思是让Rect派生于Debug trait,所以才可直接用debug模式打印信息。
标签:10,struct,name,String,Rect,rust,rect,u32 From: https://www.cnblogs.com/UFO-blogs/p/17770644.html