【环球速看料】Rust - 安装环境、基本类型、流程控制、函数、模块、泛型、所有权
安装环境、基本类型
学习Rust语言是公司同事最先开始提议的,准备用接下来的项目试试水,Rust是一个强类型编译型语言,比较偏向底层,所以开启了Rust的探索之旅。
(资料图片)
环境准备阶段
安装Rust环境
安装命令:
curl --proto "=https" --tlsv1.2 -sSf https://sh.rustup.rs | shsource $HOME/.cargo/env //设置环境变量rustc --version //查看安装版本
Cargo
Cargo 是 Rust 的构建系统和包管理器。Rust 开发者常用 Cargo 来管理 Rust 工程和获取工程所依赖的库。
Cargo 就是Vue里面的npm,php里的composer。
cargo run [项目名称]cargo build
生成的目录结构如下:
.|-- Cargo.lock|-- Cargo.toml|-- src| `-- main.rs`-- target |-- CACHEDIR.TAG `-- debug |-- build |-- deps | |-- stark-2c1445affc8ccd97 | `-- stark-2c1445affc8ccd97.d |-- examples |-- incremental |-- stark `-- stark.d
数据类型概述
类型是对二进制数据的一种约束行为。类型比起二进制数据,有许多优势:
减少开发者心智负担安全、容易优化常见的类型分类:
静态类型:在编译器对类型进行检查动态类型:在运行期对类型进行检查强类型:不允许隐式类型转换弱类型:允许隐式类型转换Rust是强类型语言。
Rust基本数据类型
1.Rust的变量
创建变量使用let关键字变量默认是不可变的,关键字前面加mut转换为可变变量常量使用const关键字定义隐藏属性2.基础数据类型
Rust是一门静态编程语言,所有变量的类型必须在编译期就被明确规定。
整数:Rust有12种不同类型的整数
对于未明确标明的类型的整数,Rust默认采用i32isize和usize根据系统不同而有不同的长度长度 | 有符号 | 无符号 |
---|---|---|
8-bit | i8 | u8 |
16-bit | i16 | u16 |
32-bit | i32 | u32 |
64-bit | i64 | u64 |
128-bit | i128 | u128 |
128-bit | i128 | u128 |
arch | isize | usize |
fn main() { let number :i8 = 32; println!("{}",number);}
浮点数型: Rust 与其它语言一样支持 32 位浮点数(f32)和 64 位浮点数(f64)。默认情况下,64.0 将表示 64 位浮点数,因为现代计算机处理器对两种浮点数计算的速度几乎相同,但 64 位浮点数精度更高。
fn main() { let x = 2.0; // f64 let y: f32 = 3.0; // f32}
布尔值:布尔型用 bool 表示,值只能为 true 或 false。大小为一个字节。
fn main() { let t = true; let f: bool = false;}
字符型:字符型用 char 表示。Rust的 char 类型大小为 4 个字节,代表 Unicode标量值,这意味着它可以支持中文,日文和韩文字符等非英文字符甚至表情符号和零宽度空格在 Rust 中都是有效的 char 值。
注意: Rust 中字符串和字符都必须使用 UTF-8 编码,否则编译器会报错。
复合类型
元组
元组用一对 ( ) 包括的一组数据,可以包含不同种类的数据:
fn main() { let a: i32= 10; let b = "A"; //创建一个元组 let mytuple:(i32,char) = (a,b); // 从元组中读取一个值 println!("{},{}",mytuple.0,mytuple.1); //解封装 let(c , d) = mytuple; println!(" {} , {} ",c , d);}
数组
数组用一对 包括的同类型数据。Rust语法规定,每个数组的类型必须相同。Rust的数组中不同于其他一些语言中的数组,具有固定长度。
数组下标以0开始,同时Rust存在越界检查。
fn main() { //初始化数组 let myarray: [u32;5] = [1,2,3,4,5]; println!("myarray[1] = {}",myarray[1]); //数组越界 //let index = "5".parse::().unwrap(); //println!("myarray[5]={}",myarray[index]); let mut mybuffer: [u32;32 * 1024] = [10;32*1024]; println!("mybuffer[1024] = {}", mybuffer[1024]); //修改数组的值 mybuffer[1024] = 13; println!("mybuffer[1024] = {}", mybuffer[1024]);}
切片
切片(Slice)是对数据值的部分引用。切片这个名字往往出现在生物课上,我们做样本玻片的时候要从生物体上获取切片,以供在显微镜上观察。
fn main() { //切片可以切数组 let myarray: [u32;5] = [1,2,3,4,5]; let slice = &myarray[0..3]; println!("slice[0] = {}, slice.length = {} ",slice[0],slice.len()); //切片还可以切字符串 let s = String::from("broadcast"); let part1 = &s[0..5]; let part2 = &s[5..9]; println!("{}={}+{}", s, part1, part2);}
Slice没有自己去存储数据,截取的都是引用数据。
结构体
结构体是多种不同数据类型的组合。它与元组类似,但区别在于我们可以为每个成员命名,可以使用struct关键字三种类型的结构。
元组结构经典的C结构无字段的单元结构结构体使用驼峰命名。
//元组结构struct Pair(i32,f32);//经典的C结构struct Peison { name:String, age:u8}fn main() { let pair = Pair(10,4.2); let person = Peison{ name: String::from("stark"), age:32 }; println!("pair.0 = {}",pair.0); println!("person.name = {}, person.age = {}",person.name,person.age);}
引用派生属性,打印结构体。
#[derive(Debug)]struct Peison { name:String, age:u8}fn main() { let person = Peison { name: String::from("stark"), age:32 }; println!("{:?}",person);}
枚举
枚举类在 Rust 中并不像其他编程语言中的概念那样简单,但依然可以十分简单的使用:
#[derive(Debug)]enum IPAddr { IPv4(u8,u8,u8,u8), IPv6(u8,u8,u8,u8,u8,u8,u8,u8,u8,u8,u8,u8),}fn main() { let localhost :IPAddr = IPAddr::IPv4(127,0,0,1); match localhost { IPAddr::IPv4(a,b,c,d) => { println!("{},{},{},{}",a,b,c,d); } _ => {} }}
Rust - 流程控制、函数
if else
Rust的if的布尔条件不用括号括起来。if所有分支返回的类型必须相同。
fn main() { let number = 3; if number < 5 { println!("条件为 true"); } else { println!("条件为 false"); }}
loop、while
Rust提供了loop一个关键字来表示无限循环。while是根据条件进行循环。
fn main() { let s = ["R", "U", "N", "O", "O", "B"]; let mut i = 0; loop { let ch = s[i]; if ch == "O" { break; } println!("\"{}\"", ch); i += 1; }}
for range
Rust的 for in 语法可以用来遍历一个迭代器,有多种方法可以创建一个迭代器,最简单也是最常见的方式:
a..b:这里将创建一个a,但不包含b的,步长为1的迭代器a..=b:这里将创建一个a,且包含b的,步长为1的迭代器fn main() { for i in 0..5 { println!("i value is {}",i); } println!("-------------"); for i in 0..=5 { println!("i value is {}",i); }}
for in 语法第二个重要的使用场景是遍历数组,但这首先将数组转化为一个迭代器,可以通过.iter()
或者.iter_mut
实现,区别是在于后者是可变的。
fn main() { let mut myarray = [1,2,3]; for i in myarray.iter(){ println!("i value is {} ",i); } for i in myarray.iter_mut() { *i *= 2; } for i in myarray.iter(){ println!("i value is {} ",i); }}
遍历关联数组:
fn main() { let myarray = ["a","b","c"]; for i in myarray.iter(){ println!("i value is {} ",i); }}
match / if_let / while_let
在Rust 中 没有 switch 语句,matcher 就是 switch 的一个变形,但比其他语言中的 switch 更强大!
let x = 5;match x { 1 => println!("one"), 2 => println!("two"), 3 => println!("three"), 4 => println!("four"), 5 => println!("five"), _ => println!("something else"),}
函数与方法
函数
函数定义以fn
为关键字,它的参数是带类型注释的,就像变量一样,如果函数返回值,则必须在箭头->
之后指定返回类型。
fn sum_number(n:u64) -> u64 { if n < 2 { n }else{ n+1 }}fn main() { println!("sumNumber is {}",sum_number(10))}
函数与闭包
Rust的闭包是一种匿名函数,它可以从它的上下文中捕获变量的值,闭包使用 ||-> 语法定义,闭包可以保存在变量中。
fn main() { let time3 = |n:u32| -> u32 { n * 3 }; println!("time3 is {}",time3(10));}
move
关键字可以从闭包环境中捕获值,它最常用的场景是将主线程中的一个变量传递到了子线程中。
use std::thread;fn main() { let hi = "hi,stark"; thread::spawn(move || { println!("stark value {}",hi); }).join();}
高阶函数 / 发散函数
在数学和计算机科学里,高阶函数至少满足一个条件的函数:
接收一个或多个函数作为输入输出一个函数在数学中它们叫做算子或泛函,高阶函数是函数式编程中一个重要概念。
fn action(method:fn(u32,u32)->u32,a: u32,b: u32) -> u32 { method(a,b);}fn add(a:u32,b:u32) -> u32 { a + b }fn sub(a:u32,b:u32) -> u32 { a - b }fn main() { println!("{}",action(add,10,20))}
发散函数
发散函数指的是永远不会被返回,它们的返回值标记!
,这是一个空类型。
Rust - 使用模块、泛型、所有权
Rust项目的代码组织包含以下三个基本概念:
Package(包)Crate(箱)Module(模块)Package
Package 用于管理一个或多个Crate,创建一个Package的方式是使用cargo new stark
命令:
[root@b0b5a9371ce4 stark]# tree.├── Cargo.toml└── src └── main.rs1 directory, 2 files
Create
Create是Rust最小单元,既Rust是编译器是以Create为最小单元进行编译的。Create在一个范围内将相关的功能组合在一起,并最终通过编译器生成一个库文件或者是二进制文件。
Module
Module允许我们将一个Create中的代码组织成独立的代码块,以便增强可读性和代码复用,同时Module还控制代码的可见性,将代码分为公开和私有两种属性,定义一个模块的关键字是mod
Module的可见性
Rust中的模块内部的代码、结构体、函数默认是私有的,但是可以通过pub关键字来改变他们的可见性,通过选择性的对外可见性来隐藏模块内部的实现细节。
比较常见的三种pub写法:
pub 成员对模块可见pub(self) 成员对模块内的子模块可见pub(crate) 成员对整个crate可见mod mod1 { pub const MESSAGE :&str = "Hello,world";}fn main() { println!("{}",mod1::MESSAGE)}
Module的引入
在文件开头使用mod 文件路径;
,第二种可以映射到一个文件夹,但文件夹中要存在mod.rs
,该文件夹可作为一个模块。
结构体的可见性
结构体的字段和方法默认是私有的,通过加上pub修饰语可使得结构体中的字段和方法可以在定义结构体外访问。要注意,与结构体同一个模块和代码的访问结构体中的字段和方法并不要求该字段是可见的。
use 绑定模块成员
使用use绑定类库,as可以指定别名。
使用super与self简化模块路径
除了使用完整路径访问模块内成员,还可以使用super与self关键字相对路径对模块进行访问。
super :上层模块self : 当前模块泛型
Rust中未指定参数类型的概念叫泛型。
函数参数的泛型
pub fn sum_number>(a:T,b:T) -> T { return a+b;}
结构体中的泛型
struct Point { x:T, y:T}struct Line { x: Point, y: Point}fn main() { println!("{}",cc::MESSAGE); println!("{}",cc::sum_number(10,20)); let pointx = Point{x:0,y:0}; let pointy = Point{x:10,y:10}; let line = Line {x:pointx, y:pointy}; println!("{},{},{}",line.x.x,line.x.y,line.y.x);}
Rust内存管理
所有权是Rust这门语言的核心概念,Rust最以为豪的内存安全就建立在所有权之上。
Rust采用了一种中间的方案RALL,它兼具GC的易用性和安全性,同时又有极高的性能。
外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5MlOioAW-1649511656829)(https://note.youdao.com/yws/res/17856/WEBRESOURCE1759d05270a5a0ada71aa6cc869b2c73)
rust所有权
Rust中每个值都绑定有一个变量,称为该值的所有者。每个值只有一个所有者,而且每个值都有它的作用域。一但当这个值离开作用域,这个值占用的内存将被回收。fn main() { let s2:String; { let s1 = String::from("Hello,world"); s2 = s1; //println!("s1 value {}",s1); //value borrowed here after move } println!("s2 value {}",s2);}
借用
在有些时候,我们希望使用一个值而不拥有这个值,这种需求在函数调用的时候特别常见。
fn echo(s:String){ println!("{}",s);}fn main() { let s = String::from("hello.world"); echo(s); println!("{}",s);}
Rust一个变量只有一个所有权。
fn echo(s:&String){ println!("{}",s);}fn main() { let s = String::from("hello.world"); echo(&s); println!("{}",s);}
不可变引用与可变引用
默认情况下,引用是不可变的,如果希望修改引用的值,需要使用&mut
。
fn change(s: &mut String){ s.push_str("chenged!")}fn main() { // 要借用的变量s也需要是可变的变量 let mut s = String::from("hello.world"); change(&mut s); println!("{}",s);}
同一时间内,至多有一个可变引用。
fn main() { let mut s = String::from("hello.world"); let s1_ref = &mut s; let s2_ref = &mut s; println!("{}",s1_ref); println!("{}",s2_ref);}
生命周期注解
生命周期注解不会改变之前生命周期的长短,它还是原来的生命周期,注解是给编译器看的,拥有相同的生命周期注解,生命周期都是一样的。
fn bigger (str1:&str,str2:&str) -> &str { if str1 > str2 { str1 }else{ str2 }}fn main() { println!("{}",bigger("a","b"));}
结构体当中的生命周期注释
#[derive(Debug)]struct Person { name: String}fn main() { let p = Person{ name:String::from("zhangyu") }; println!("{:?}",p );}
推荐
- 专访郑州航空工业管理工程学院副院长宋志刚:物流枢纽间的竞争将愈加激烈
- 光储充算一体化发展亟待提速!记者实测“一秒一公里”超级储充
- 瑞德智能董秘回复:公司已拥有逆变器等新能源产品的发明专利和实用新型专利
- 单片机代码不变,hex却变了?
- 存储芯片下行周期有望见底 A股上市公司加速布局
- 当赛季包揽助攻王+FMVP:历史仅詹姆斯和魔术师两人
- 「图解牛熊股」本周最牛股大涨逾110% 华为、芯片板块涨幅“遥遥领先”
- 茶村(关于茶村简述)
- 盘活乡村“沉睡”资源 塘垭山礼野奢帐篷营地“花开”武陵源
- 科幻作家陈楸帆:科技发展遵循曲线规律 以想象力战胜周期
- 中国云市场半年观察:运营商中程发力,下沉市场价格鏖战,打好AI牌成为制胜关键?
- 懂车帝发布年轻用户汽车洞察报告 00后比90后更青睐国产品牌和新能源车
- 消息称出口车型去除车尾英文标语 比亚迪回应:部分车型更改
- 用手机做什么可以挣钱(用手机做什么赚钱)
- 段向东与阿联酋环球铝业首席执行官阿卜杜纳赛尔•卡班举行视频会谈
- 涡轮增压器存在隐患 部分进口奥迪汽车被召回
- 陕西能源:9月7日融资买入723.58万元,融资融券余额3.25亿元
- 都市新闻版责任编辑
- 英派斯(002899):9月8日技术指标出现观望信号-“黑三兵”
- 受超强台风“苏拉”影响,香港数百航班取消
- 莘野(关于莘野简述)
- 我国载人航天工程全线拥有4000多件发明专利 广泛应用于各行各业
- 新鲜出炉!2023年海南自贸区上市龙头企业有哪些?(9月1日)
- 助人,让社会更美好议论文
- 鹿城夜跑欢乐童行 三亚夏日亲子季圆满落幕
- 山高新能源(01250)中标山东省菏泽市某标段风电项目
- 这支视障青年组建的本土乐队即将开启秋天的第一场演唱会
- 爱帝宫(00286.HK)中期股东应占亏损收窄61.54%至2365.6万港元
- undertale com undertale au官网
- 奏响就业曲 打通致富路——来自新疆阿克苏地区的一线调研
- 厦门市:实施首套房贷款“认房不用认贷”政策
- 机构观点:加蓬国内局势突变预计不会影响油市
- 观影《孤注一掷》,宝鸡高新公安警民共赴“反诈之约”
- 骁龙765g与尺寸1000plus的性能对比
- 东亚银行(00023.HK)回购19.92万股 涉资约222.83万港元
- TCL流媒体服务TCLtv+北美上线,Google TV电视用户可免费收看
- 王清宪主持召开省政府第十八次常务会议
- 鲁山县花715万元建牛郎织女雕塑 最新通报:县住建局局长免职
- 三国名马和马主人(三国名马)
- 二季度机构持股新动向!“宁王”取代茅台 成最受青睐个股!
- 2023年8月30日乙二醛水溶液价格最新行情预测
- 你可知道这样会让我心碎什么歌(“你可知道这样会让我心碎”是哪首歌里的歌词)
- 美机构研发出能杀死所有实体癌瘤的药物
- 365天免布线插电 乐橙智能Wi-Fi电池球机K9E正式上市 具体是什么情况?
- 旅马大熊猫谊谊、升谊抵川:状态平稳,将隔离检疫30天
- 里昂:上调海底捞评级至“跑赢大市” 目标价升至24.8港元
- 无关三镇!名记李璇:今天能等个通报!球迷:某球队或被取消冠军
- 德钦县开展全国经济普查单位清查业务培训
- 《正是橙黄橘绿时》第四章 一万种夜莺-4
- 「产业互联网周报」ARM向美国证交会提交IPO申请;钉钉首次公布商业化核心进展;阿里云开源通义千问多模态大模型Qwen-VL
- 国际识局:中美建立“新沟通渠道”,释放哪些重要信号?
- 关于传国玉玺的记载 可能是中国最搞笑的伪史
- 联动科技(301369):8月29日北向资金增持31万股
- 北京宏福苑小区二手房价格(北京宏福苑北区二手房)
- 8月29日盟固利(301487)龙虎榜数据:游资上海溧阳路上榜
- 金融助力文旅复苏,2023全省金融服务与文旅企业恳谈对接会在遂宁举行
- 抖音陈奕迅演唱会主持人 抖音陈奕迅
- 国际看点|毒品吸食者成群 美国肯辛顿大道如上演僵尸电影!
- 东方甄选淘宝首秀“翻车”:烟薯红包标错紧急下架,官方认赔
- 安科瑞:已与东南亚和欧洲市场当地系统代理商合作
- 郏县:心系师生出行难 修路便民暖人心
- 全明星街球派对球员强度排行榜
- 金石亚药:2023年上半年扣非归母净利翻倍增长,核心产品需求大幅增加
- 中国烟草,紧急声明
- 西甲-格列兹曼闪袭莫拉塔梅开二度 马竞6人破门7-0血洗
- 火车站旅客醉酒担心财物遗失,找到民警“求保管”
- 三大基地全面投产运行 富煌钢构上半年净利润增长23%
- 中报观察 | 商汤大模型争流
- 德必集团:上半年营收5.23亿元 同比增长28.84%
- 华友钴业跌6.64% 中泰证券在其高位喊买入
- 河南研学游成主流 郑州开封洛阳迎来强势反弹
- 金杯v19 p0340故障码排除方法
- 农发行湖北省分行 绘就荆楚和美乡村崭新画卷
- 短期重磅利好,中长期仍要回归基本面
- 美银证券:维持华润燃气“买入”评级 目标价降至28.5港元
- 【镜头里的青海】云端之上瞰西宁
- 政策“组合拳” 提振投资者信心
- 每年让利基民142亿,超百家公募献上“诚意”,是何信号?
- 呼和浩特加快实施“智慧乳业”行动
- 近似数的概念初中(近似数的概念)
- 酸菜肉片汤的家常做法(酸菜肉片)
- 争光股份(301092.SZ)半年报净利润5134.44万元,同比增长7.49%
- 起亚EV6上市!硬核科技大秀成都车展!
- 仇保兴:京津冀都市圈应建立空间协调落实机制,不能光画图不落实|快讯
- 什么叫股指期货交易
- 总储架规模5.27亿元,首期发行1亿元!全国首单技术产权(技术交易)ABS上市交易
- 全球大米价格飙升!世界最大大米出口国又出手了
- 火影忍者炎之中忍试验!鸣人VS木叶丸!!(火影忍者炎之中忍试验)
- 普特彼他克莫司软膏治疗什么(普特彼)
- 山水比德董秘回复:作为美丽中国与生态文明的探索者与践行者,公司近年来布局全国20+城市
- 小组赛-比塔泽15+10 格鲁吉亚轻取佛得角取开门红
- 本周生猪价格微降,机构称当前市场需求相对有限
- 菲律宾电子签证系统率先在上海试行
- 业界热议大模型落地金融业:创新应用场景 加快数字化转型
- 离婚案一方不同意离婚怎么办呢?
- 康冠科技08月25日获深股通增持2.31万股
- 中国(河北)—韩国生态环境产业对接交流会举行 河北现场签约总投资约218.24亿元
- 08月25日猪评: 全面暂停进口水产品,猪价或将迎来上涨?
- 西子洁能(002534)周评:本周跌6.85%,主力资金合计净流出2131.67万元
- 女性占西藏高级专业技术人员42.9%
X 关闭
行业规章
X 关闭