编写一个 Rust 宏重复,它可能会也可能不会初始化结构体字段

2024-01-26

我正在尝试编写一个列出多个结构字段的宏,但有条件地仅从列表中的某些字段创建初始化程序代码。具体来说,可能看起来像这样:

#[test]
fn test() {
    #[derive(PartialEq, Debug)]
    struct Foo {
        bar: usize,
    }

    let a = Foo {
        bar: 0,
    };

    let b = test!(Foo {
        bar: 0,
        #[nope] baz: 0,
    });

    assert_eq!(a, b);
}

Foo没有字段baz,以及#[nope]应该告诉宏对该字段不执行任何操作;真正的宏会使用baz在一个位置而不是另一个位置,并且还有其他“属性”需要处理。

这是接受调用但不忽略的基线宏baz:

macro_rules! test {
    (
        $struct:ty {
            $($(#[$modifier:ident])? $field:ident: $value:expr,)*
        }
    ) => {
        {
            // don't mind this syntax workaround
            type X = $struct;
            X {
                $($field: $value,)*
            }
        }
    };
}

现在,我知道对不同的重复使用不同的规则的技巧是将每个重复委托给辅助规则。这是相同的宏,将常规变体和不变体分开:

macro_rules! test {
    (
        $struct:ty {
            $($(#[$modifier:ident])? $field:ident: $value:expr,)*
        }
    ) => {
        {
            type X = $struct;
            X {
                $($field: test!(@field $(#[$modifier])? $field: $value),)*
            }
        }
    };

    (
        @field $field:ident: $value:expr
    ) => {
        $value
    };

    (
        @field #[nope] $field:ident: $value:expr
    ) => {
        $value
    };
}

但这在这里没有帮助,因为我只委托$value, not $field: $value,。但我不能委托整个事情,因为从语法上讲,这不是宏可以生成/不能生成的一个标记树(?)。

有没有办法使用这个或另一个技巧来实现这一目标?如果可能的话,最好避免使用过程宏。


None

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

编写一个 Rust 宏重复,它可能会也可能不会初始化结构体字段 的相关文章

随机推荐

  • SQL 代理命令行未保存

    我有一个 SSIS 包 我正在尝试安排时间 我在 SQL Server 代理下创建了一个新作业 在作业步骤的 命令行 选项卡上 我选择 手动编辑命令行 当我在作业步骤中从一个选项卡切换到另一个选项卡时 更改会被保留 但每当我退出并保存作业时
  • 在 Ruby 中编写一个在不同行获取参数的方法

    在使用 Rails 时 我发现可以调用这样的方法 lot Lot new do u u grade id grade id u company id company id u type id type id u sale id sale i
  • 如何从 AsyncTask 返回布尔值?

    我有一些 EditText 用户输入 ftp 地址 用户名 密码 端口和 testConnection 按钮 如果连接成功建立 它将返回布尔值 true boolean status ftpConnect address username
  • 在eclipse中创建android项目时出错

    我是 Android 开发人员的新手 我正在学习 但是当我创建一个新项目时 显示了这个错误 在错误日志中我有很多错误 我不知道如何在这里导出所有错误 在项目资源管理器中 我的项目显示如下 我不知道如何解决所有这些错误 感谢您的帮助 并对我的
  • rspec测试协会

    我想在我的 rspec 控制器测试中测试员工是否与公司关联 我想在我的create工作人员财务主任的行动 staff companies lt lt current company Where current company从会话变量中收集
  • Flutter - 仅当内容高度大于屏幕高度时才启用滚动

    默认情况下 我在主体小部件中采用 ListView 或 SingleChildScrollView 因此 如果内容较少 则会滚动内容 我只想在内容大于屏幕高度时启用滚动 如果内容高度小于屏幕高度 需要禁用滚动 double physical
  • 镜头和类型系列

    我遇到了使用问题Control Lens和 一起使用时的数据类型 XTypeFamiliesGHC 杂注 LANGUAGE TemplateHaskell LANGUAGE TypeFamilies import Control Lens
  • 当 Android 中的软键盘出现在视图前面时,布局应该向上

    我有一个问题 我有一个登录屏幕 当我们单击编辑文本时 软输入键盘会覆盖两个小部件 一个是 TextView 另一个是登录按钮 它们位于相对布局中 但我希望当我们选择任何编辑文本时整个相对布局应该向上 并且所有小部件都在 Android 默认
  • 向 TextView 添加底线边框 - iOS

    添加底线边框的最佳方法是什么TextView具有动态高度 我试过这个 func addBottomBorderWithColor color UIColor width CGFloat let border CALayer border b
  • 如何获取 $date + 5 来排除周末?

    我有一些页面需要设置将来的日期 由变量设置的 2 天或 5 天 该日期只需计算周一至周五 不包括周末 到目前为止我所拥有的 tts 是 2 或 5 的变量 具体取决于页面 Today date N m y NewDate date l t
  • 在 Cassandra 列中存储 JSON 字符串的有效方法?

    卡桑德拉新手问题 我正在使用 REST 调用从社交网站收集一些数据 所以我最终得到了 JSON 格式的数据 JSON 只是我表中的列之一 我试图找出存储 JSON 字符串的 最佳实践 首先我想到使用map类型 但 JSON 包含字符串 数字
  • 如何阻止 while 循环无限运行?

    不知道如何阻止这个 while 循环无限重复 我在用着hasNextInt检查用户输入是否为 int 如果未输入 int 则循环将无限重复 public static void validatingInput Scanner scan ne
  • 选择另一个表中不存在的值

    我有两张桌子 Table A ID 1 2 3 4 Table B ID 1 2 3 我有两个请求 我想选择表 A 中表 B 没有的所有行 在本例中是第 4 行 我想删除表 B 中没有的所有行 我正在使用 SQL Server 2000 你
  • Sonar:复制/高可用性或集群解决方案

    SonarQube Sonar 是否支持复制 高可用性解决方案 我的目标是在当前实例运行的计算机上出现硬件故障时拥有一个故障转移 SonarQube 实例 目前不支持 SonarQube 集群 目前您能做的只是准备好虚拟机 以便在 Sona
  • 如何对数据表中的列进行排序。 JSF 2.0

    我正在 jsf 2 0 中构建一个 WebApp 它用于存储信息并将其显示在屏幕上 所以我放入了一些 http java sun com jsf html 数据表来显示一些列表 我的 Java 代码返回一个列表 然后将它们显示在屏幕上 但现
  • 从 SSIS 目录执行包时无法访问网络共享

    我目前遇到一个问题 我可以从 SQL Server Data Tools 完美地执行包 但在尝试从 SSIS 目录中执行时出现以下错误 文件系统任务 错误 发生错误 并显示以下错误消息 访问路径 xxxxxxxx xxxx 被拒绝 我使用相
  • 定义Windows Phone中PhoneTextBox的样式

    我正在重写 PhoneTextBox 的样式 将默认背景更改为 透明 将前景更改为 白色 将 BorderBrush 更改为 白色 因为我想设计一个深色主题 但是出现了一个问题 文本输入指示器消失了 我感谢原因是文本输入指示器的前景是黑色的
  • apache Drill 是否可以执行更新、删除、插入操作

    众所周知 apache Drill 很容易查询 但我有一些问题如下 First 如果apache Drill可以对HDFS执行更新 删除 插入操作 Second 如果第一个问题的答案是肯定的 我如何使用 apache Drill 在 HDF
  • Objective-c:使用带有导航栏的第二个视图启动应用程序

    我正在为 iPad 创建一个应用程序 我创建了 3 个带有导航栏的视图 但我想不在第一个视图中启动我的应用程序 而是在第二个视图中启动我的应用程序 我该怎么办 您可以设置UI导航控制器 http developer apple com li
  • 编写一个 Rust 宏重复,它可能会也可能不会初始化结构体字段

    我正在尝试编写一个列出多个结构字段的宏 但有条件地仅从列表中的某些字段创建初始化程序代码 具体来说 可能看起来像这样 test fn test derive PartialEq Debug struct Foo bar usize let