【问题标题】:How do I iterate arguments of a macros in Rust?如何在 Rust 中迭代宏的参数?
【发布时间】:2019-12-24 12:09:29
【问题描述】:

我正在尝试创建一个宏来填充具有固定大小的向量的第一个元素。其余元素应为零。我写道:

const SIZE: usize = 3;

#[derive(Debug)]
struct MyVec {
    data: [f32; SIZE]
}

macro_rules! my_vec {
    ($($x:expr),*) => [{
        let mut data: [f32; SIZE] = [0.0; SIZE];
        for (i, e) in x.enumerate() {
            data[i] = e;
        }
        MyVec { data }
    }]
}

fn main() {
    let v = my_vec![1.0, 2.0];
    println!("{:?}", v);  // must be MyVec { data: [1.0, 2.0, 0.0] }
}

看起来我试图以错误的方式迭代参数。我该如何解决?

【问题讨论】:

    标签: rust


    【解决方案1】:

    你可以这样做,

    const SIZE: usize = 3;
    
    #[derive(Debug)]
    struct MyVec {
        data: [f32; SIZE],
    }
    
    macro_rules! my_vec {
        ( $( $x:expr ),* ) => {
            {
                let mut data: [f32; SIZE] = [0.0; SIZE];
                let mut index = 0;
                $(
                    #[allow(unused_assignments)]
                    {
                        data[index] = $x;
                        index = index + 1;
                    }
                )*
                MyVec { data }
            }
        };
    }
    
    fn main() {
        let v = my_vec![1.0, 2.0];
        println!("{:?}", v); // print MyVec { data: [1.0, 2.0, 0.0] }
    }
    

    $(...)* 中的代码将针对每个匹配项进行扩展。

    【讨论】:

    • 谢谢,它成功了。为什么我会在index = index + 1 行中收到带有文本warning: value assigned to 'index' is never read 的警告?
    • @Fomalhaut 这将扩展到let mut index = 0; data[index] = …; index = index + 1; data[index] = …; index = index + 1; data[index] = …; index = index + 1;,最后一个index = index + 1 是创建警告的那个。我已经编辑了答案以忽略警告。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-11-09
    • 1970-01-01
    • 2021-11-14
    • 2023-04-08
    • 2018-11-23
    • 2021-11-19
    相关资源
    最近更新 更多