2016-11-15 2 views
2

구조체 슬라이스를 반복 할 때 얻을 수있는 값은 참조 (괜찮습니다)이지만 경우에 따라 을 여러 위치에 (*var)으로 써야하는 것은 귀찮습니다.녹에서 레퍼런스 대신 슬라이스의 값을 반복 하시겠습니까?

변수를 다시 선언하는 것을 피할 수있는 더 좋은 방법이 있습니까?

fn my_fn(slice: &[MyStruct]) { 
    for var in slice { 
     let var = *var; // <-- how to avoid this? 

     // Without the line above, errors in comments occur: 

     other_fn(var); // <-- expected struct `MyStruct`, found reference 

     if var != var.other { 
      // ^^ trait `&MyStruct: std::cmp::PartialEq<MyStruct>>` not satisfied 
      foo(); 
     } 
    } 
} 

참조 : actual error output (더 비밀).

+0

포인터없이 원하는대로 할 수 있습니다. –

+0

아니요,이 경우가 아닙니다. 일부 작업은 작동하지만 충분하지는 않습니다. – ideasman42

+0

'var'를 그대로 사용하는 대신에'let var = * var'을 사용해야 할 곳에 예제를 제공 할 수 있습니까? –

답변

14

당신은 the pattern에서 destructuring하여 참조를 제거 할 수 있습니다

그러나
// | 
// v 
for &var in slice { 
    other_fn(var); 
} 

이에만 작동 Copy에 대한 을 -types! Copy이 아닌 Clone 유형 만있는 경우 수는cloned() 이터레이터 어댑터를 사용하십시오. 자세한 내용은 Chris Emerson의 답변을 참조하십시오. Clone이 아닌 유형이 있다면 그럴 기회가 없습니다.

+0

정답입니다. –

9

반복 가능 항목을 사용할 수있는 경우 값에 직접 반복 할 수 있습니다. Vec::into_iter()을 사용하십시오. 조각으로, 당신은 cloned를 사용할 수 있습니다

fn main() { 
    let v = vec![1, 2, 3]; 
    let slice = &v[..]; 
    for u in slice.iter().cloned() { 
     let u: usize = u; // prove it's really usize, not &usize 
     println!("{}", u); 
    } 
} 

을이 분명히 복제 가능한되는 항목에 의존; 하지만 그렇지 않다면 아마 참조를 원할 것입니다.

+0

이것은 Lukas의 답변만큼 효율적이지 않습니다. 또한,'slice'는 변경 가능하지 않으므로 반복자가 사용되는 동안'slice' 자체는 복제되지 않으므로 복제가 필요하지 않습니다. –

+2

@EliSadoff 실제로 두 가지 솔루션 모두 동일한 최적화 된 어셈블리 출력을 생성합니다. 전체 슬라이스 나 반복자가 복제되지는 않지만 각 요소가 복제됩니다. –

+0

@LukasKalbertodt 네 말이 맞아. 나는 또한 이것이 설명하는'복제'대'복사'에 대해서 생각하지 않았다. –

관련 문제