RUST学习第二天

108 阅读3分钟

RUST语法的骨架

三部分:
属性部分(#![…])
行分隔符号:(;)
块分隔符号:({})

语句和表达式

首先,我门要明确一个概念:

编程中的表达式和语句

  • 说到表达式,大多数人想到的可能是数学表达式;程序中的表达式也类似,他是一个由操作符和操作数组成的算术或逻辑运算式,它可以产生一个值。
  • 语句是命令式编程语言的一个语法单元,表示程序要执行的操作。程序是有一个或多个语句序列,语句可能包含内部组件。

所以:"表达式"(expression)是一个单纯的运算过程,总是有返回值;

"语句"(statement)是执行某种操作,没有返回值。

广义上每行都是一个语句;

根据每行做的事情的不同,可以把语句分成:

  • 声明语句(定义结构体,定义函数,引入模块,赋值)

  • 流程控制语句(条件分支,循环,case语句)

  • 表达式语句(用于求值)

  • 宏语句(文本替换,生成代码)


对应到 RUST中

RUST中的概念

了解为什么RUST是面向表达式的语言?

RUST借鉴了函数式编程语言,函数式编程语言的特点即:

  • 面向表达式。通过计算表达式进行求值,而不是修改语句。

函数式编程要求,只使用表达式,不使用语句。

也就是说,每一步都是单纯的运算,而且都有返回值。

在RUST中:

  • RUST中行分隔符(;),块分隔符({})是最基本的表达式。

    • 既然是表达式,他就有返回值,这里行分隔符(;表达式) 永远返回自身的单元类型【()】
  • RUST中,行分隔符(;表达式) 只在块表达式最后一样才会求值,其他时候是链接符。

  • RUST中,块表达式只对最后一行表达式进行求值。

看下下面代码加深下对上面几句的理解:

fn main(){
;
;
{
()
}
{
();
use std:vec:Vec; //返回单元值类型()
}
();
&{;};//返回 &()
;
;// 这里返回() 是main的返回值。上面其他的 ;是分隔符
}

这就能理解rust中的隐式返回了

fn main(){
	let a = 1;
	let b = 2;
	a+b // 
}
  • 首先块表达式只对最后一样进行求值:这里是 a+b 表达式,得到一个值,作为main的 返回值。
  • 其次 如果在a+b 后面加上 ;的话,这里最后一个表达式就成了 ; 这时候返回值变成了()
fn plus(i:&u32)->u32{
	let i = i+1;
	i //这里不加分号,返回的就是块表达值的最后一个表达式(i),如果加了分号,返回的就是单元类型了()
}

RUST中一切皆表达式;

  • 除了基本的声明语句之外,其他的基本都属于表达式;
  • 字面量是表达式,路径是表达式,流程控制是表达式。

看下例子:

fn main(){
   //默认返回单元类型	
}

-----
println!() //宏 返回单元类型
-----

fn main(){
	for i in 1..102{
		if i%15 == 0{println!("fizzbuzz")}
		else if i%3==0{println!("fizz")}
		else if i%5==0{println!("buzz")}
		else{println!("{}",i)} 
	}
}

//这里 if 返回值是 单元类型。for返回值也是单元类型。和 main 返回类型一致

//使用 match表达式实现:
fn main(){
	for i in 1..102 {
		match(i%3,i%5){
			(0,0)=>println!('fizzbuzz'),
			(0,_)=>println!('fizz'),
			(_,0)=>println!('buzz'),
			(_,_)=>println!("{}",i)
		}
	}
}

由于 表达式都是 有具体值的,一个具体的值就会有他的类型,所以可以说:RUST一切皆类型。

RUST就是通过对类型进行各种检查实现内存安全和并发安全。

了解rust的求值规则很有必要。