rust语言学习_incomplete

rust语言学习

  • 初见
    • 前言
    • cargo
      • 项目创建
      • 版本
      • 编译
      • 库的引用
      • 文档
    • 语言
      • 语法规则
      • 变量
      • 数据类型
        • 整形
        • 字符类型
        • 元组
        • 数组
      • 控制流
      • 函数
      • 所有权
      • 结构体
      • 枚举
        • Option与空值
        • match控制流
        • 实例

初见

前言

我看的是rust官方教程的翻译版(感谢翻译的大佬们),这里记录下学习的过程。

cargo

cargo是rust的构建系统和包管理器

项目创建

创建项目的过程感觉很新奇,使用cargo new后,会自动创建目录结构,而且还自动创建了git仓库。

wsl@My-win:~/project/hello_catgo$ ls -lar
total 24
drwxrwxr-x 2 wsl wsl 4096 Jun 17 20:30 src
-rw-rw-r-- 1 wsl wsl  180 Jun 17 20:30 Cargo.toml
-rw-rw-r-- 1 wsl wsl    8 Jun 17 20:30 .gitignore
drwxrwxr-x 6 wsl wsl 4096 Jun 17 20:30 .git
drwxrwxr-x 5 wsl wsl 4096 Jun 17 20:30 ..
drwxrwxr-x 4 wsl wsl 4096 Jun 17 20:30 .

src里面新建了一个打印helloworld的rs文件

版本

看下Cargo.toml里的内容,

wsl@My-win:~/project/hello_catgo$ cat Cargo.toml
[package]
name = "hello_catgo"
version = "0.1.0"
edition = "2021"

这里面连版本号都有。

编译

编译命令是cargo build,这个看起来没啥,但是好处是开发环境的统一,checkout一个仓库,直接就可以build(甚至不限定目录)。虽然./configure&&make也差不多,但是那个更自由,文件目录不统一。
cargo run可以编译加执行:

wsl@My-win:~/project/hello_catgo$ cat Cargo.lock
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 3

[[package]]
name = "hello_catgo"
version = "0.1.0"
wsl@My-win:~/project/hello_catgo$ cargo run
    Finished dev [unoptimized + debuginfo] target(s) in 0.00s
     Running `target/debug/hello_catgo`
Hello, world!

cargo check可以检查错误而不编译。
build自带debug,release。

库的引用

引用库就只需要加一行,就会自动去下载了,而且还会固化版本号:

[dependencies]
rand = "0.8.5"

rust的库可能有y版本号兼容的规则,即x.y.z-x.y+1.0(不含)的版本可以兼容。

文档

可以使用cargo doc --open来查看本地依赖的文档。

语言

语法规则

方法调用,刚开始看到这段代码我真的很疑惑:

io::stdin()
        .read_line(&mut guess)
        .expect("failed to read line");

这是个啥东西,后来我懂了,应该就是一直调用方法而已,只不过没写在一行,我试了一下写在一行也是可以的(虽然不符合标准格式):

io::stdin().read_line(&mut guess).expect("Failed to read line");

变量

变量默认不可变,使用mut使变量可变。
变量值隐藏,可以定义新的来覆盖旧的,这个问题一定程度上解决了强类型和弱类型语言的矛盾,而且隐藏使得不可变的变量有了可变的机会。
变量值无需声明类型,而是自动推导。常量必须指定类型。
需要区别其与c++中重载,重写,覆盖的区别。

数据类型

标量:整型,浮点,布尔,字符
复合:元组,数组

整形

以占用存储空间为分类,明确每个数字的类型。
多种数字书写形式,包括可以使用分隔符来方便阅读。

字符类型

rust里面的字符占4字节。

元组

元组一旦声明,其类型和长度就不可变了

数组

rust中的数组长度不可变,他在栈上分配空间。
初始化方式:

let a = [3; 5];

变量名为 a 的数组将包含 5 个元素,这些元素的值最初都将被设置为 3。
针对越界的处理,从语言层面限制,会直接panic,而不是去继续访问。

控制流

if ,条件必须是bool
loop 循环标签
for循环 迭代器
break可带值

函数

语句(Statements)是执行一些操作但不返回值的指令。 表达式(Expressions)计算并产生一个值。

    let y = {
        let x = 3;
        x + 1
    };

函数返回值

fn five() -> i32 {
    5
}

fn main() {
    let x = five();

    println!("The value of x is: {x}");
}

rust中函数可以嵌套定义:

fn main() {
    fn five() -> i32 {
        5
    }
    println!("five() 的值为: {}", five());
}

所有权

在运行时,所有权系统的任何功能都不会减慢程序。

Rust 中的每一个值都有一个 所有者(owner)。
值在任一时刻有且只有一个所有者。
当所有者(变量)离开作用域,这个值将被丢弃。

浅拷贝 深拷贝 移动 引用 借用
引用的值默认不可变。可以创建可变引用,但是只能创建一个,这是为了避免数据竞争。在拥有不可变引用时不能同时拥有可变引用,这个是由作用域决定的(而非生命周期?),由编译器来检查。
这个可变引用和不可变引用有种读写锁的感觉。
Slice类型:str,没有所有权,是一类引用。

结构体

字段初始化简写语法
结构体更新语法
元组结构体
类单元结构体
关联函数,方法语法和getters

枚举

枚举将一个值成为一个集合之一的方法。在c中,枚举的本质仍然是数字类型的集合, 他更像是define的强化版,而在rust中,枚举的成员不在是一个具体的值,他只是多种成员的的集合。

Option与空值

match控制流

穷尽的匹配
other与_分支

实例

函数返回结果抽离,有个专门的Result类型,他是一种枚举类型,值为OK或Err。Result类型拥有expect方法,如果不调用甚至会出现告警:

wsl@My-win:~/project/guess_num/src$ cargo check
    Checking guess_num v0.1.0 (/home/wsl/project/guess_num)
warning: unused `Result` that must be used
  --> src/main.rs:9:5
   |
9  | /     io::stdin()
10 | |         .read_line(&mut guess);
   | |______________________________^
   |
   = note: this `Result` may be an `Err` variant, which should be handled
   = note: `#[warn(unused_must_use)]` on by default
help: use `let _ = ...` to ignore the resulting value
   |
9  |     let _ = io::stdin()
   |     +++++++

warning: `guess_num` (bin "guess_num") generated 1 warning
    Finished dev [unoptimized + debuginfo] target(s) in 0.06s

下面给出了无效处理返回值的类型,感觉像匿名变量?这里可以看出rust的一个理念,专门化,具体化,每个错误都不是未定义的,都是确定的。
比较结果也专门化,使用Ordering,std::cmp::Ordering 是一个枚举,它的成员是 Less、Greater 和 Equal。

你可能感兴趣的:(rust,rust,学习,开发语言)