为什么对不明确的数字进行方法调用会导致错误?

2023-11-30

在参考文献中文字表达, I see

如果标记没有后缀,则表达式的类型由类型推断确定:

  • ...
  • 如果程序上下文对类型约束不足,则默认为带符号的 32 位整数i32.
  • ...

但我从以下代码中得到一个错误:

let i = (-100).abs();
error[E0689]: can't call method `abs` on ambiguous numeric type `{integer}`

为什么对不明确的数字进行方法调用会导致错误? '-100' 的类型不是推断为i32?


让我们首先引用所有相关部分那一页(强调我的):

  • 如果可以从周围的程序上下文唯一确定整数类型,则表达式具有该类型。
  • 如果程序上下文对类型约束不足,则默认为带符号的 32 位整数i32.
  • 如果程序上下文过度限制类型,它被认为是静态类型错误。

现在,由于动词“约束”的使用方式,此描述可能会产生误导。人们通常熟悉受特征约束的泛型类型,但引用可能不应该以这种方式解释。类型欠约束和过度约束是指对类型施加额外要求的情况,这些要求必须通过类型推断来考虑,这种情况在调用该类型的方法时发生。

所以不,它不适用于任何形式的约束超过一个类型。这是一个反例。

fn is_signed(x: impl num_traits::Signed) {
    let _ = x.abs(); // can call abs thanks to Signed trait
}

fn main() {
    is_signed(-5);
}

这段代码(操场)可能看起来“约束”-5要求对号码进行签名,并且由于我们已经实现了Signed对于多个整数类型,这应该是不明确的。但实际上它确实可以编译从 Rust 1.63.0 开始。

另一个特殊的例子。

trait Foo {}

impl Foo for u8 {}
impl Foo for u16 {}

fn foo(_: impl Foo) {}

fn main() {
    foo(5);
}

这段代码(操场) 无法编译,但原因并非您所期望的:

error[E0277]: the trait bound `i32: Foo` is not satisfied
 --> src/main.rs:9:5
  |
9 |     foo(5);
  |     ^^^ the trait `Foo` is not implemented for `i32`
  |
  = help: the following other types implement trait `Foo`:
            u16
            u8
note: required by a bound in `foo`
 --> src/main.rs:6:16
  |
6 | fn foo(_: impl Foo) {}
  |                ^^^ required by this bound in `foo`

据称,整数的类型推断机制采用了默认类型i32,即使唯一可能的实现是u8 and u16。无论如何,这将是另一个模棱两可的情况。

然而,当人们试图这样做时,情况就明显不同了。调用一个方法直接关联到一个类型,如(-100).abs()。从调用该方法的那一刻起abs,甚至存在多个整数类型,编译器将整数视为具有过度约束的类型,并且与该推理一致,发生了静态类型错误。编译器对此提供了不同的解释,具体体现为错误E0689.

对不明确的数字类型调用了方法。

无论如何,该代码无法编译的真正原因是编译器无法识别该特定情况下整数的类型,并且没有将整数类型默认为i32。 Rust 参考不是该语言的标准参考,可能不完整或包含过时的信息。除了过度约束和约束不足的误导性概念之外,参考文献中的描述与撰写本文时编译器的行为相匹配。此时,我们很可能正在处理另一个编译器的细微差别。

也可以看看:

  • Rust 中默认的整数类型是什么?
  • Rust 中的文字整数值有特定类型吗?
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

为什么对不明确的数字进行方法调用会导致错误? 的相关文章

随机推荐

  • WPF NotifyPropertyChangeds 是否编组到调度程序?

    如果我更新一个在绑定控件调度程序之外的线程上抛出 INotifyPropertyChanged 的 属性 更新会被强制编组到该调度程序吗 BackgrounWorker Run gt blah Blahness 2 notifies pro
  • 从对象数组构造 TypeScript 类型

    我有数据库表的以下架构列 用于西瓜数据库 const columns name created at type number isOptional true name created by type string name is corru
  • 在Java中通过URL调用PHP文件

    我正在尝试开发一个 Android 应用程序 它调用 php 文件来查询并从数据库中提取数据 该 URL 可以在我的手机上通过网络浏览器访问 但我似乎无法从下面的 java 代码中调用它 任何人都可以帮助我从我的 Java 代码调用我的 P
  • wpf 窗口的默认字体大小是如何确定的?

    据我了解 在 WPF 中 控件使用的字体大小由父控件确定 除非定义了覆盖 鉴于我没有在应用程序中的任何位置定义字体大小 我假设默认字体大小是为顶级窗口配置的 该值是否由应用程序运行所在的系统决定 如果是 则在哪里 或者它是由某些内置的 WP
  • jQuery 调整两侧大小

    我会尝试用文字说清楚 我想知道是否有一种方法可以使用 jquery ui resizing 来同时调整 4 个边上的对象的大小 以便使对象的中心保持在相同的位置 这是沙箱http jsfiddle net V79Ge 所以 它很像aspec
  • 将 char* 交给 std::string 进行管理(最终释放内存)

    我必须使用一个库函数 为生成的字符串分配一些内存并返回一个char 期望调用者最终释放内存free Example declaration of the library function char foo Example usage aut
  • 在 Java 中使用 LIMIT 命令和预处理语句时出现 MySQL 语法错误

    我正在用 Java 编写代码 我想每次运行此代码时都从 MySQL 表中获取下一行 我第二次运行此代码是这样的 String timh1 1 String timh2 2 PreparedStatement st null String s
  • 空手道:重复请求

    我想重复 6 次场景的 post 请求 Given url
  • 如何根据表中的多列获取唯一记录

    考虑下表 primaryKey id activity template creator created 1 1 3 5 x 2011 10 13 2 2 4 2 y 2011 10 15 3 2 4 7 z 2011 10 24 4 2
  • 使用 WMI 和 C# 检测机器是否在线或离线

    我使用vs2008 winxp 在局域网中使用Win2003服务器 我想要在winxp中安装一个应用程序来检测win2003机器是否在线或离线 以及启动时是否离线 我有这个参考资料 还有更多参考资料 代码示例和最佳实践吗 http dani
  • 将树序列化为 Json 对象

    我有以下课程 树节点 cs public class TreeNode IEnumerable
  • Task.WhenAny 用于无故障任务

    的描述Task WhenAny方法说 它将返回第一个完成的任务 即使它出错了 有没有办法改变这种行为 以便它返回第一个成功的任务 像这样的东西应该可以做到 可能需要一些调整 尚未测试 private static async Task
  • 如何将整数数组连接成逗号分隔的字符串

    其实我有两个问题 如何将整数数组连接成逗号分隔的字符串 1 2 3 gt 1 2 3 如何将整数数组转换为字符串数组 1 2 3 gt 1 2 3 arraylist New Object system collections arrayl
  • 如何使用自动布局设置 tableHeaderView (UITableView) 的高度?

    在过去的三四个小时里 我一直用这个把头撞在墙上 但我似乎无法弄清楚 我有一个 UIViewController 里面有一个全屏 UITableView 屏幕上还有其他一些东西 这就是为什么我不能使用 UITableViewControlle
  • SonarQube Java插件3.7分析错误

    我最近升级到 SonarQube 5 2 和 Java 插件 3 7 在分析我的项目期间遇到以下错误 我已经删除了类文件名 但它是一个非静态的私有内部类 该分析适用于 Java 插件版本 3 5 和 3 6 仅在 3 7 下失败 有人可以帮
  • 如何实现通话记录的 ContentObserver

    我想知道是否有办法知道呼叫的内容提供商是否已更改 我的意思是 如果我拨打电话或接听电话 它会返回一个 标志 表明新日志已添加到通话记录中 或者 Android 存储有关通话信息的位置 因为 当我拨打电话时 Android 会将号码 联系人姓
  • 我无法将数据读入 R

    我正在尝试读入一些数据 该数据是一个文本文件 如下所示 2009 08 09 2009 08 15 0 2 0 2009 08 16 2009 08 22 0 1 0 2009 08 23 2009 08 29 0 1 0 2009 08
  • 如何从 Jquery 调用 ActionResult

    这是我的 ActionResult UsersModel um new UsersModel um Users userRepository GetAllUsers um UserCustomers userRepository GetAl
  • 为什么应用背景颜色时文本输入会更改其边框属性?

    这是一个例子 我正在 FF 3 6 中查看 输入为background transparent与未触及的边界有不同的边界 http jsfiddle net Pa2Kd 我的假设是 当样式未更改时 将使用本机 Win32 控件及其默认设置
  • 为什么对不明确的数字进行方法调用会导致错误?

    在参考文献中文字表达 I see 如果标记没有后缀 则表达式的类型由类型推断确定 如果程序上下文对类型约束不足 则默认为带符号的 32 位整数i32 但我从以下代码中得到一个错误 let i 100 abs error E0689 can