自学内容网 自学内容网

Rust学习(二):rust基础语法Ⅰ

Rust学习(二)——rust基础语法Ⅰ:

1、关键字:

了解编程语言的同学都清楚,关键字在一门编程语言中的意义,所谓关键字就是语言的创造者及后续开发者们,以及定义好的具有特殊含义和作用的单词,需要注意的是在变量及函数等名命时要避开这些关键字,以避免可能出现逻辑冲突,每种编程语言所拥有的关键字数量并不相同,Rust目前有39个关键字:

Selfenummatchsuperas
externmod traitasyncfalse
movetrueawaitfn   mut
typebreakforpubunion
constifrefunsafecontinue
implreturn usecratein
selfwheredynletstatic
whileelseloopstruct        # 注意Selfself是两个不同的关键字

很多关键字和其他编程语言种的关键字功能类似,比如:for,move,if等,但是也有一些独特的关键字,体现了语言的设计者的精妙构思,比如match在Rust种功能强大,但是在C/C++中对应的switch的功能就相对偏弱。

2、注释:

在编程中注释的作用自然不必多说,就有一句著名的格言展示了注释的重要性:一个程序员在编程时,只有他和上帝知道代码的作用,过了三天就只有上帝知道这段代码的作用了!(doge),因此在编程中加入注释,可以帮助阅读代码的人(也包括作者)更好的理解代码编写过程中的复杂逻辑,从而做出针对性的优化,Rust和C/C++、python等语言相比注释功能更加完整和强大!

Rust的注释有两大类:普通注释和文档注释。

①普通注释:

rust提供了单行和多行普通注释两种方法(和C/C++保持一样):

// 单行注释

/*
*
*多行注释
*多行注释
*
*/

②文档注释:

rust非常关注文档和测试,因此提供了专门的文档注释,用于在注释中直接编写文档和测试代码,同时Rust文档采用的时Markdown格式,因此在编写测试文档时,需要注意使用Markdown形式:

//! 生成库文档,用于说明整个模块的功能,一般置于模块开头
/// 生成库文档,用于说明函数和结构体功能,一般置于说明对象的开头

//! Math 模块
//!
/// #add 函数
/// 该函数为求和函数
///
/// # Example 
/// use math::add;
/// assert_eq!(3, add(1, 2));
fn add(x: i32, y: i32) -> i32 {
    // 求和
    x + y
}

3、Rust名命风格:

名命风格并不是强制要求,但是应该被看做时一种规范而被遵循。Rust推荐采用驼峰式命名(UpperCamelCase)来表示类级别的内容,而采用蛇形命名(snake_case)类描述值级别的内容,可见下表:

项 约定
包 snake_case
类型UpperCamelCase
特性UpperCamelCase
枚举UpperCamelCase
函数snake_case
方法snake_case
构造函数(无特殊要求)或者new
转换函数(无特殊要求)
宏snake_case
局部变量SCREAMING_SNAKE_CASE
静态变量SCREAMING_SNAKE_CASE
常量sanke_case
类型参数UpperCamelCase
生命周期lowercase

下面这个例子给大家提供了一个很好的参考:

// 枚举
enum Result<T,E> {
    Ok(T),
    Err(E),
}
// 特性trait
pub trait From<T> {
    fn from<T> -> Self;
}
// 结构体:
struct Rectangle {
    height: i32,
    width: i32,
}
impl Rectangle {
    //构造函数
    fn new(height: i32, width: i32) ->Self {
        Self {height, width}
    }
    
    // 函数
    fn calc_area(&self) ->i32 {
        self.height * self.width
    }
}

// 静态变量和常量
static NAME: &str = "kew";
const AGE: i32 = 25;

// 宏定义:
macro_rules! add{
    ($a:expr, $b:expr) => {
        {
            $a + $b
        }
    }
}

// 变量及宏使用:
let sum_of_nums = add!(1,2);

4、常量:

Rust中的常量和C++中的常量基本一致,特点是不可修改,不可覆盖,使用const关键字定义:

//常量定义,类似于C/C++中的#define(宏定义)
const AGE: i32 = 1984;
// AGE = 1985; 报错, 常量不允许被修改
// const AGE: i32 = 1996; 报错,AGE已经被定义过,不能被覆盖

5、变量:

rust中变量使用let定义,变量是一个绑定到一个名称且允许改变(可覆盖)的值,但在Rust中有一些不同,默认直接使用let定义的变量不可修改,使用mut关键字方可修改:

let x: f64 = 3.14;
// x = 6.28; 报错,变量不可修改
let x: f64 = 6.28; //变量可以被覆盖

let mut y: f64 = 256.01;
y = 3.28;
let y: f64 = 2024; // 使用mut关键字之后变量可修改,可覆盖。

6、静态变量:

静态变量是一种特殊的变量,可以被修改,但是不能被覆盖,同时其是否可修改同样取决于是否使用mut关键字:

static NAME: &str = "rust";
// NAME = "new"; 报错,未使用mut不可以被改变
static mut NUM: i32 = 12;
unsafe {
    NUM += 1;  // 可以看到static mut 修改是在unsafe中完成的,所以日常开发中使用较少
}
// static NAME: &str = "Cargo"; 报错,静态变量不可覆盖
// static NUM: i32 = 13; 错误,静态变量不可覆盖

7、数据类型:

学习一门编程语言,一定会从数据类型入手,这点就好比学习C语言的char、array类型,python的整型、浮点型等,如果学习一门编程语言却不知道数据类型,未免太不专业了!

数据类型是一门语言的基础,所有复杂的模块都是由基础数据类型构建而来的,Rust的基础数据类型分为标量类型和符合类型两大类型,标量类型代表一个单独的值,复合类型则是将多个值组合成一个值的类型(有点绕,不要着急,下文会仔细解释!)

(1)标量类型:

Rust中有四种基本的标量类型:整型、浮点型、布尔型和字符型。

①整型:

整型即整数:没有小数部分的的数字,根据长度和符号,可分为12类,其中i表示有符号整型,u表示无符号整型:

长度有符号无符号
8   i8u8
16   i16u16
32         i32      u32
64   i64      u64
128        i128     u128
arch       isize    usize

这里需要特别指出,isize和usize是指和计算机架构相匹配的整型长度,如64位机器isize和usize都是64位长度,32位机器isize和usize都是32位长度的。

②浮点数:

rust中的浮点数分为:f32和f64两种类型(都是有符号的),默认为64位。

③布尔类型:

和其他类型一致,都是true和false两类(doge)。

④字符型:

rust的字符和C语言中的char是一致的,注意:字符使用单引号声明,而字符串使用双引号声明,字符串属于数组类型。

// Unicode 标量:字符型
let c = 'a';
// 数组字符串:
let str_c = "hello rust";

(2)复合类型:

①元组:

元组是一种能够将多个类型的数据值组合成复合值得类型,即所谓将多个值合并为一个值。一旦声明元组得长度就不可改变,元组使用圆括号包裹,并用逗号分隔。为了从元组中获取值,你可以使用模式匹配和点符号(类似于其他语言得索引,从下标0开始)。

let tup: (i32, i32,i64) = (1, 2, 3);

// 使用模式匹配:
let (x, y, z) = tup;

let tup2:(i32, i32, i32) = (2,3,4);
let zero = tup2.0 // 点符号获取值
②数组:

Rust中得数组和C/C++中得数组类似,数组中得每一个元素必须保持一致,且长度也不可以改变。但是Rust为我们提供了可变数组,使用Vec定义得数组,允许增长长度,大部分时候,我们使用得也是Vec定义得数组:

// 定义数组
let numbers = ["a", "b", "c"];
let digits[i32;5] = [0, 1, 2, 3, 4, 5]; // 通过[type;num]定义数组
let zeros = [0;5]; //创建一个包含5个0得数组

let bundary = numbers[0];

(3)数据类型转换:

Rust中得数据类型大多数是可以互相转换得,比如将i8转换为i16就是合理转换,但rust中不支持原生类型之间得隐式转换(将字符型转换为浮点型),必须使用as关键字进行显性转换。

fn main() {
    let decimal:f32 = 61.234;
    // let integer: u32 = decimal; 错误!不能进行隐式转换
    let integer = decimal as u32; //正确!,使用as进行显示转换
}

更加复杂得类型中,Rust提供了From和Info两个trait进行转换:(trait是一个难点,后面会具体介绍)

pub trait From<T> {
    fn from<T> ->Self;
}
pub trait Into<T> {
    fn into<T> ->Self;
}

struct Complex {
    real:i32,
    imag:i32
}

impl From<i32> for Complex {
    fn from(real:i32) ->Self {
        Self {real, imag:0}
    }
}

fn main() {
    let c1: Complex = Complex::from(2);
    let c2: Complex = 2.into();
    println!("c1:{:?}, c2:{:?}", c1, c2);
}

原文地址:https://blog.csdn.net/2301_77286822/article/details/143697618

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!