学习rust语言宏之macro_rules!

学习rust语言,必然不可避免要了解和熟悉宏。rust语言的宏功能非常强大,通过合理的编写利用宏,可以简化程序代码,也少写很多代码。今天我们先从宏的基本编写方法macro_rules开始:

1,格式

rust 复制代码
macro_rules! $name {
    $rule0 ;
    $rule1 ;
    $rule2 ;
    // ...
    $ruleN ;
}

大括号里面的规则(rule)有点类似rust中的match匹配,匹配其中的一条rule,则用其中的内容生成具体代码。

规则(rule)涉及到一个匹配格式:(pattern)和{expansion}可以是任何类型的组,其中的括号和大括号根据官网说法是约定俗成。

rust 复制代码
($pattern) => {$expansion}

2,简单测试

我们编写一个简单宏进行以下测试

rust 复制代码
#[macro_export]
macro_rules! add10 {
    ($a:expr) => {
        {
            $a+10
        }
    };
}

fn testadd(){
    println!("the add10 value is {}", add10!(10));
}

我们编写一个对于输入数字加10的宏,我们输入10,最终打印输出为20.

3,详解

3.1,宏捕获

规则中可以通过多种多样的语法进行匹配捕获,匹配符合时,将运行后续语句,并将结果传输到一个变量中,最终输出。

规则捕获中,以美元符号($)开始,后跟:符号,最后跟捕获类型。捕获类型有如下这些:

  1. item:一个项目,如函数、结构体、模块等。
  2. block:一个块(即一个语句块和/或一个表达式,用大括号括起来)
  3. stmt:一个声明
  4. pat:模式
  5. expr:表达式
  6. ty:类型
  7. ident:标识符
  8. path: 路径(例如 , , , ...)foo``::std::mem::replace``transmute::<_, int>
  9. meta:一个元项;里面的东西和属性#[...]``#![...]
  10. tt:单个标记树

下面这个宏,它将输入捕获为表达式(rust本来就是表达式语言),我们写的add10宏也是将输入捕获为表达式:

rust 复制代码
macro_rules! one_expression {
    ($e:expr) => {...};
}

例如我们也可以写一个对于任何输入数字进行与100相乘的宏mul100

rust 复制代码
macro_rules! mul100 {
    ($a:expr) => {
        {
            $a*100
        }
    };
}

我们也可以捕获多个输入:

rust 复制代码
macro_rules! moreadd {
    ($a:expr, $b:expr, $c:expr) => {
        {
            $a+$b+$c
        }
    };
}

3.2,重复项

模式(pattern)中可以包含重复项,而通过重复项的方法,我们可以匹配和捕获多个输入,这样通过宏极大的扩展了程序的功能。

重复项一般通过$(.....) sep rep的形式出现

  • $是 Literal Dollar 代币。
  • ( ... )是重复的括号分组模式。
  • sep是可选的 separator token。常见示例包括 和 。,``;
  • rep是必需的重复控件 。目前,这可以是 (表示 零个或多个重复) 或 (表示一个或多个重复) 。您不能编写 "zero or one" 或任何其他更具体的计数或范围。*``+

下面我们通过官网的介绍说明的类似vec!宏的编写方法:

rust 复制代码
#[macro_export]
macro_rules! my_vec {
    ( $( $x:expr ),* ) => {
        {
            let mut temp_vec = Vec::new();
        $(
            temp_vec.push($x);
        )*
        temp_vec
        }
    };
}

fn test_micro(){
    let v = my_vec!(1,2,3,4);

    for i in v{
        println!("the is is {}",i);
    }
}
相关推荐
bug和崩溃我都要9 分钟前
Qt 封装 libmpv 全功能视频播放器开发指南
开发语言·qt·音视频
SNKXD_112 分钟前
2026品牌运营团队AI营销培训:TOP5轻量化课程适配常态化技能升级学习
大数据·人工智能·学习
郝学胜-神的一滴15 分钟前
Qt 高级开发 018:复刻经典登录界面布局与窗口美化全解析
开发语言·c++·qt·程序人生·用户界面
郝亚军21 分钟前
IEEE 754 单精度浮点的SEM表示
开发语言·c++·算法
zhangjw3428 分钟前
第15篇:Java多线程零基础入门,进程线程、线程创建方式、线程生命周期、线程安全彻底吃透
java·开发语言·面试
蝈理塘(/_\)大怨种29 分钟前
类和对象 (上)
java·开发语言
小新同学^O^41 分钟前
简单学习 --> 指令微调
人工智能·学习·llm·指令微调
風清掦1 小时前
【STM32学习笔记-14】WDG看门狗 - 14.2 WWDG窗口看门狗
笔记·stm32·单片机·嵌入式硬件·学习·fpga开发
小新1101 小时前
qt creator 将qInfo的输出日志写入日志文档,方便查看
开发语言·qt
G_dou_1 小时前
Linux 搭建 Rust 开发环境:从 rustup 安装到 Cargo 镜像
linux·rust