#rust
Вопрос:
У меня есть следующий тип
struct Test<Args> {
// ...
phantom: PhantomData<Args>,
}
это должно хранить, наряду с содержимым, параметр типа для определения аргументов функции, которые будут переданы позже.
Я использую его следующим образом:
#![feature(unboxed_closures, fn_traits)]
impl<Args> Test<Args> {
fn update<F>(amp;mut self, args: Args, f: F)
where
F: FnOnce<Args>
{
//...
let value = f.call_once(args);
// ...
}
}
К сожалению, я не могу использовать его для заимствованных ценностей. Мне нужно было бы уметь делать что-то вроде
type MyTest = Test<for<'a> (amp;'a u32, amp;'a u32)>;
let mut t: MyTest = ...;
t.update((amp;5, amp;8), |lhs, rhs| lhs rhs);
Но Test<for<'a> (amp;'a u32, amp;'a u32)>
это неверный синтаксис.
В настоящее время мой обходной путь состоит в том, чтобы изменить Test
вместо fn
этого тип, а затем ограничить его рядом с другим типом на сайте вызова следующим образом:
#![feature(unboxed_closures, fn_traits)]
struct Test<F> {
// ...
phantom: PhantomData<F>,
}
impl<F> Test<F> {
fn update<Args, F2>(amp;mut self, args: Args, f: F2)
where
F: FnOnce<Args>,
F2: FnOnce<Args>,
{
//...
let value = f.call_once(args);
// ...
}
}
type MyTest = Test<for<'a> fn(amp;'a u32, amp;'a u32)>;
let mut t: MyTest = ...;
t.update((amp;5, amp;8), |lhs, rhs| lhs rhs);
Но это относительно некрасиво и требует изменения публичного интерфейса. Я также не уверен, есть ли какие-либо проблемы с противопоставлением в его аргументах. fn
Есть ли лучший способ добиться этого, сохраняя оригинальную подпись (или близкую к ней)?
Я не хочу использовать сам сайт вызова F
в универсальных типах, так как мне нужно, чтобы он был универсальным в методе, а не в типе, так как он может быть закрытием с заимствованными значениями, в то время как тип может быть статическим.
Ответ №1:
Способ выражения MyTest
псевдонима типа выглядит следующим образом:
type MyTest<'a> = Test<(amp;'a u32, amp;'a u32)>;
Комментарии:
1. К сожалению , мне нужно
MyTest
работать в течение каждой жизни'a
, а не в течение какой-то определенной жизни'a
, как в обходном пути, поэтому это не работает2. @FilipeRodrigues Я вижу, вы хотите
Test
, чтобы вам ввели, что он будет приниматьamp;T
аргументы, которые являются общими в течение их жизни, так как они будут выведены наupdate()
сайте вызова. К сожалению, я не думаю, что Rust поддерживает этот вариант использования; ваш синтаксис, вероятно, был бы подходящим для этого, если бы это было так.