DST coercions fall over with UFCS
#![feature(core, rc_weak)]
use std::cell::RefCell;
use std::rc::{Rc, Weak};
trait Baz { fn get(&self) -> i32; }
impl Baz for i32 { fn get(&self) -> i32 { *self } }
fn main() {
let a: Rc<RefCell<i32>> = Rc::new(RefCell::new(42));
let c1: Weak<RefCell<Baz>> = Rc::downgrade(&a); // Doesn't work
let c2: Weak<RefCell<Baz>> = Rc::downgrade(&a) as Weak<_>; // works
let c3: Weak<RefCell<Baz>> = a.downgrade(); // works
}
CC @nrc
This is difficult: the "expected type" propagation is too eager here. It should be just a hint, only with the instantiated generic signature being enforced. Might be a bit hard to handle, but a different variant of
Expectationthat doesn't error on type mismatches, could work. The argument handling does coercion, and could also ignore a type mismatch with the hint there, as long as the orignal formal super-type is unified with the expression's type. Then a coercion would be enabled on the return type.Eduard-Mihai Burtescu at 2015-08-17 23:21:16
Triage: no real change. The flags can be removed, c3 doesn't work because downgrade is no longer a method, c1 still fails.
Steve Klabnik at 2017-02-07 20:27:12
Triage: here's the full code, today:
use std::cell::RefCell; use std::rc::{Rc, Weak}; trait Baz { fn get(&self) -> i32; } impl Baz for i32 { fn get(&self) -> i32 { *self } } fn main() { let a: Rc<RefCell<i32>> = Rc::new(RefCell::new(42)); let c1: Weak<RefCell<dyn Baz>> = Rc::downgrade(&a); // Doesn't work let c2: Weak<RefCell<dyn Baz>> = Rc::downgrade(&a) as Weak<_>; // works }and the error:
error[E0308]: mismatched types --> src/main.rs:9:52 | 9 | let c1: Weak<RefCell<dyn Baz>> = Rc::downgrade(&a); // Doesn't work | ^^ expected trait Baz, found i32 | = note: expected type `&std::rc::Rc<std::cell::RefCell<dyn Baz>>` found type `&std::rc::Rc<std::cell::RefCell<i32>>`Steve Klabnik at 2019-12-25 16:00:36