Open
Description
Hello rust team!
I crossed the following compiler error.
There is a lifetime elision problem on closures on some specific conditions
- they accept as input a struct with a lifetime
- they are transmited to a function accepting multiple of them as generics
Quite hard to explain with words, so here is the simplified example:
The code:
pub struct InodeMapper;
pub struct ValueCreatorParams<'a> {
pub child_name: &'a u32,
}
impl InodeMapper {
pub fn batch_insert<F, G>(
&self,
f1: F,
f2: G
)
where
F: for <'a> Fn(ValueCreatorParams<'a>) -> u32,
G: for <'b> Fn(ValueCreatorParams<'b>) -> i32
{
todo!()
}
}
fn test_batch_insert_large_entries_varying_depths() {
let mapper = InodeMapper{};
let f1 = |_| 1;
let f2 = |_| 2;
// *** ERROR ON FOLLOWING LINE ***
mapper.batch_insert(f1, f2);
}
The error
implementation of `Fn` is not general enough
closure with signature `fn(test::ValueCreatorParams<'2>) -> u32` must implement `Fn<(test::ValueCreatorParams<'1>,)>`, for any lifetime `'1`...
...but it actually implements `Fn<(test::ValueCreatorParams<'2>,)>`, for some specific lifetime `'2`rustc[Click for full compiler diagnostic](rust-analyzer-diagnostics-view:/diagnostic%20message%20[4]?4#file:///home/alogani/Coding/easy_fuser/src/types/test.rs)
implementation of `FnOnce` is not general enough
closure with signature `fn(test::ValueCreatorParams<'2>) -> u32` must implement `FnOnce<(test::ValueCreatorParams<'1>,)>`, for any lifetime `'1`...
...but it actually implements `FnOnce<(test::ValueCreatorParams<'2>,)>`, for some specific lifetime `'2`rustc[Click for full compiler diagnostic](rust-analyzer-diagnostics-view:/diagnostic%20message%20[5]?5#file:///home/alogani/Coding/easy_fuser/src/types/test.rs)
The solution:
Fully qualify the types of the closure arguments (for both)!
fn test_batch_insert_large_entries_varying_depths() {
let mapper = InodeMapper{};
let f1 = |_: ValueCreatorParams| 1;
let f2 = |_: ValueCreatorParams| 2;
mapper.batch_insert(f1, f2);
}
And now it works like a charm !
Meta
rustc --version --verbose
:
rustc 1.82.0 (f6e511eec 2024-10-15)
binary: rustc
commit-hash: f6e511eec7342f59a25f7c0534f1dbea00d01b14
commit-date: 2024-10-15
host: x86_64-unknown-linux-gnu
release: 1.82.0
LLVM version: 19.1.1
## Suggestions
Obviously, it has a solution, but I fill the bug report, because:
- this is a situation where I don't understand why the compiler can't infer the lifetime. (Maybe there is a reason a good reason and it shall not be corrected? To be honest, I am not sure to understand the intrinsics)
- the error is not explicit (it took me several hours to isolate correctly the cause of the problem in my more complex codebase, I thought the problem were on signatures of the receiving function). So is there an improvement possible on compiler message ? Especially the compiler don't say how it infers a different lifetime for the two closures to help resolve the problem.
Thanks!