如何在不查看代码的情况下读取生命周期错误?

Fed*_*ico -2 rust borrow-checker

我收到以下生命周期错误:

error[E0495]: cannot infer an appropriate lifetime for autoref due to conflicting requirements
  --> prusti-viper/src/procedures_table.rs:42:40
   |
42 |         let mut cfg = self.cfg_factory.new_cfg_method(
   |                                        ^^^^^^^^^^^^^^
   |
note: first, the lifetime cannot outlive the anonymous lifetime #1 defined on the method body at 40:5...
  --> prusti-viper/src/procedures_table.rs:40:5
   |
40 | /     pub fn set_used(&mut self, proc_def_id: ProcedureDefId) {
41 | |         let procedure = self.env.get_procedure(proc_def_id);
42 | |         let mut cfg = self.cfg_factory.new_cfg_method(
43 | |             // method name
...  |
135| |         self.procedures.insert(proc_def_id, method);
136| |     }
   | |_____^
note: ...so that reference does not outlive borrowed content
  --> prusti-viper/src/procedures_table.rs:42:23
   |
42 |         let mut cfg = self.cfg_factory.new_cfg_method(
   |                       ^^^^^^^^^^^^^^^^
note: but, the lifetime must be valid for the lifetime 'v as defined on the impl at 22:1...
  --> prusti-viper/src/procedures_table.rs:22:1
   |
22 | impl<'v, P: Procedure> ProceduresTable<'v, P> {
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   = note: ...so that the expression is assignable:
           expected viper::Method<'v>
              found viper::Method<'_>

error: aborting due to previous error
Run Code Online (Sandbox Code Playgroud)

无需查看代码,只需阅读错误消息,是否可以了解哪些生命周期/引用/借用是指错误消息?这是用我的问题注释的消息:

错误[E0495]:由于需求冲突,无法推断autoref (autoref是什么?)的适当生命周期

注意:首先,生命周期(生命周期?)不能超过40:5时方法体上定义的匿名生命#1 (&mut selfok之一) ...

...所以引用(哪个引用?)不会比借来的内容(借用内容?)更长寿?

但是,生命周期必须对生命周期'v有效,因为在22:1的impl上定义... (为什么这些约束?)

例如,我在寻找一个解释,如"在错误信息E0495不能活得比匿名寿命#1总的寿命寿命self,换句话说,#1再次".

通过查看现有的回答类似的问题(/sf/answers/2486346551/,/sf/answers/2160834161/,/sf/answers/2888999571/),我找不到错误信息所指的解释.有时答案只写"在这种情况下,生命是'a",但我想知道如何理解它是,'a而不是其他一些'b.其他时候答案涉及对源代码的推理,但这对我来说将是以下步骤之一:首先阅读消息并理解它所指的是什么,然后理解错误(在这种情况下,可能是冲突的生命周期要求) ,然后查看代码并尝试修复错误.

Dan*_*lme 5

由于需求冲突,无法推断autoref的适当生命周期

这是错误的关键部分.一生中有两个(或更多)要求,它们会发生冲突."autoref"表示通过调用方法获取的引用&self.引用的代码行指示哪个方法调用是错误的.

注意:首先,生命周期不能超过40:5在方法体上定义的匿名生命#1

这是第一个相互冲突的要求."生命周期"是指第一条消息中提到的那个:它试图推断的那个,对于这个autoref.它不能比你调用方法的对象寿命更长.引用的代码表示该对象的生命周期.在这种情况下,生命周期是错误行所在的整个方法,因为您借用的对象是该方法的成员&mut self.

注意:...所以参考不会超过借来的内容

这只是进一步解释了."那个参考" - 你试图采取的autoref - 不能超过&mut self引用的对象.

注意:但是,生命周期必须对生命周期'v有效,因为在22:1的impl上定义...

这里的"但"引入了第二个要求,它与第一个要求相冲突.

你问"为什么这些约束?",编译器马上解释:

注意:...以便表达式可赋值:
expected viper :: Method <'v>
found viper :: Method <'_>

有问题的作业是错误行中的作业.您是分配的结果new_cfg_method来cfg."预期"是作业的左侧cfg,必须是类型viper::Method<'v>."found"是右侧,是方法调用的结果,它具有类型viper::Method<'_>.'_表示编译器尝试推断的生命周期.也就是说,这是你随后使用的方式cfg,这意味着它必须具有生命周期'v.为什么这取决于错误消息中未引用的代码.

要解决此问题,您需要执行以下操作之一:

  1. 切出第一个要求.更改,new_cfg_method以便其结果的生命周期与您调用它的对象的生命周期无关:可能通过删除它包含的一些引用.
  2. 删除第二个要求.更改使用的代码,cfg这样就不需要生命周期'v.同样,这可以通过删除一些引用来实现viper::Method.

如果你不能做任何一件事,你可能需要引入Cell或其他东西来动态地而不是静态地管理生命周期.