2017-12-29 14 views
1

のは、私が素数との力のベクトルを持っているとしましょう:`&(&usize、&u32)`のようなパターンにどのように一致させるのですか?

let mut primes: Vec<usize> = ...; 
let mut powers: Vec<u32> = ...; 

それは事実primes.len() == powers.len()ことがあります。

私は(このコードは、適切な参照文献とderefsが欠落している)ユーザーに0の対応するパワー値を持つ素数のリストを返すしたいと思います:

primes.iter().zip(powers) 
    .filter(|(p, power)| power > 0) 
    .map(|(p, power)| p) 
    .collect::<Vec<usize>>() 

コンパイラは多くのことを不平を言っています、あなたが想像しているように。特に、filterはタイプ&(&usize, &u32)の引数を受け取りますが、パターンマッチングでは正しく参照解除されていません。私はコンパイラが示唆しているさまざまなパターンを試しました(例えば、&(&p, &power)、これは私にとって最も理にかなっていますが)。 power > 0の比較を問題なく行うことができるように、そして最後にVec<usize>を収集できるように、パターンマッチングを正しく実行するにはどうすればよいですか?作品

答えて

2
primes.iter().zip(powers) 

iter()参照することにより反復するので、あなたは素数のため&usize要素を取得します。 OTOH .zip()は、所有値を反復する.into_iter()を呼び出します。したがって、べき乗はu32であり、これらの反復子は(&usize, u32)を超える繰り返しを呼び出します。技術的には、このような混合型を反復することに何も問題はありませんが、不一致が混乱する可能性があります。または.iter().cloned()を素数に使用して参照を避けるか、または.zip(powers.iter())を呼び出して参照として取得することができます。

2つ目は.filter()が(それはそれを変更して返すことができます)所有の値(_,_)で(それが唯一の彼らに「見える」以降)を参照&(_,_)でアイテムを取り、.map()ということです。整数のような小さな値について

、あなたは通常、このようなこれらのメソッドを使用したい:

.filter(|by_ref| { 
    let item = *by_ref; 
}) 
&item上記の例では同等ですので、クロージャの構文は、 |pattern: type|であること

.filter(|&item| …) 
.map(|item| …) 

注意を

1

:私も参照して要素を生成するpowers.iter()を使用

fn main() { 
    let primes: Vec<usize> = vec![2, 3, 5, 7]; 
    let powers: Vec<u32> = vec![2, 2, 2, 2]; 

    let ret = primes.iter().zip(powers.iter()) 
      .filter_map(|(p, pow)| { // both are refs, so we need to deref 
       if *pow > 0 { 
        Some(*p) 
       } else { 
        None 
       } 
      }) 
      .collect::<Vec<usize>>(); 

    println!("{:?}", ret); 
} 

注意。また、両方のイテレータでcloned()を使用し、値を操作することもできます。

関連する問題