2015-11-06 3 views
0

я столкнулся с проблемой в этой ситуации (код здесь работоспособен):Как определить, какой родовой тип Rust не может сделать вывод?

extern crate rand; 
use rand::{Isaac64Rng, SeedableRng, Rng}; 
pub trait GeneticAlgorithm<R, Ins, C> : Clone where R: Rng { 
    fn mate(parents: (&Self, &Self), rng: &mut R) -> Self; 
    fn mutate<F>(&mut self, rng: &mut R, mutator: F) where F: FnMut(&mut Ins); 
    fn call<F>(&self, program: F) where F: FnOnce(&C); 
} 

pub struct Mep<Ins> { 
    instructions: Vec<Ins>, 
    unit_mutate_size: usize, 
    crossover_points: usize, 
} 

impl<Ins> Mep<Ins> { 
    //Generates a new Mep with a particular size and takes a closure to generate random instructions 
    pub fn new<I>(unit_mutate_size: usize, crossover_points: usize, instruction_iter: I) -> Mep<Ins> 
     where I: Iterator<Item=Ins> { 
     Mep{instructions: instruction_iter.collect(), unit_mutate_size: unit_mutate_size, 
      crossover_points: crossover_points} 
    } 
} 

impl<Ins> Clone for Mep<Ins> 
    where Ins: Clone { 
    fn clone(&self) -> Self { 
     Mep{instructions: self.instructions.clone(), unit_mutate_size: self.unit_mutate_size, 
      crossover_points: self.crossover_points} 
    } 
} 

impl<R, Ins> GeneticAlgorithm<R, Ins, Vec<Ins>> for Mep<Ins> where R: Rng, Ins: Clone { 
    fn mate(parents: (&Mep<Ins>, &Mep<Ins>), rng: &mut R) -> Mep<Ins> {} 
    fn mutate<F>(&mut self, rng: &mut R, mut mutator: F) where F: FnMut(&mut Ins) {} 
    fn call<F>(&self, program: F) where F: FnOnce(&Vec<Ins>) { 
     program(&self.instructions); 
    } 
} 

fn main() { 
    let mut rng = Isaac64Rng::from_seed(&[1, 2, 3, 4]); 
    let (a, b) = { 
     let mut clos = || Mep::new(3, 3, rng.gen_iter::<u32>().map(|x| x % 10).take(10)); 
     (clos(), clos()) 
    }; 
    let mut c = Mep::mate((&a, &b), &mut rng); 
    c.mutate(&mut rng, |ins: &mut u32| *ins = 2); 
    c.call(|x: &Vec<u32>| panic!()); 
} 

Rust утверждает, что он не может вывести тип где-то, но я не знаю, как определить тип затвора, если это вопрос, и я не в состоянии определить, какой конкретный общий параметр вызывает вопрос:

main.rs:48:7: 48:36 error: unable to infer enough type information about `_`; type annotations or generic parameter binding required [E0282] 
main.rs:48  c.call(|x: &Vec<u32>| panic!()); 
       ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 

Какой универсальный параметр необходимо указать, и как это может быть определено? Если это невозможно сделать, как можно указать предполагаемый признак: GeneticAlgorithm<Isaac64Rng, u32, Vec<u32>>

Если кто-то хотел бы создать оригинальный код, я hosting it on GitHub (commit b0b24482fb7fc71da9c23cd1481ea09c9edd867e).

+1

Смотрите также [предыдущий вопрос] (http://stackoverflow.com/questions/33569621/which-generic-parameter-must-be-specified) в этой серии. – Shepmaster

ответ

1
impl<R, Ins> GeneticAlgorithm<R, Ins, Vec<Ins>> for Mep<Ins> where R: Rng, Ins: Clone { 
    // ... 
} 

Этот impl блок реализует GeneticAlgorithm для Mep<Ins> для всех возможных значений R. Это означает, что существует множество реализаций признака GeneticAlgorithm для конкретного Mep<Ins>. Когда вы вызываете методы mate и mutate, компилятор может разрешить определенную реализацию из аргументов, но при вызове call компилятор не может решить конкретную реализацию, так как R не имеет ограничений.

Чтобы решить эту проблему, переместите общий параметр R в методы mate и mutate.

pub trait GeneticAlgorithm<Ins, C> : Clone { 
    fn mate<R>(parents: (&Self, &Self), rng: &mut R) -> Self where R: Rng; 
    fn mutate<R, F>(&mut self, rng: &mut R, mutator: F) where F: FnMut(&mut Ins), R: Rng; 
    fn call<F>(&self, program: F) where F: FnOnce(&C); 
} 

impl<Ins> GeneticAlgorithm<Ins, Vec<Ins>> for Mep<Ins> where Ins: Clone { 
    fn mate<R>(parents: (&Mep<Ins>, &Mep<Ins>), rng: &mut R) -> Mep<Ins> where R: Rng { panic!() } 
    fn mutate<R, F>(&mut self, rng: &mut R, mut mutator: F) where F: FnMut(&mut Ins), R: Rng { panic!() } 
    fn call<F>(&self, program: F) where F: FnOnce(&Vec<Ins>) { 
     program(&self.instructions); 
    } 
}