2015-01-21 3 views
1

저는 F #에 비교적 익숙하며 여전히 배우고 있습니다. float 배열의 모든 NAN의 인덱스를 int 배열 옵션으로 반환하는 함수를 작성하려고합니다.f # float 배열에있는 모든 NaN의 인덱스를 얻습니다.

let arr = [1.0; 2.0; nan: 2.0; 4.5; nan; nan; 3.0;] 

나는 Array.tryFindIndex를 사용하여 첫 번째 nan의 색인을 반환하는 fct가 있습니다. 하지만 지금은 붙어있어 다른 배열을 배열에서 빼내기 위해 무엇을해야할지 모르겠다. 이 같은 내 코드는 모습입니다 : 그것은 반복 조건을 적용 확실히 가능

let indexOfOneNan (arr:array<float>) = 
    arr 
    |> Array.tryFindIndex (fun f -> nan.Equals(f)) 
    |> fun b -> match b with 
      | Some (x) -> Some ([|x|]) 
      | None  -> None 

답변

4

을 만족뿐만 아니라 최초의 모든 요소를 ​​검색하기 위해,하지만 새로운 배열의 할당을 포함하는 것 각 단계마다. 이것은 매우 효율적이지 않을 것입니다.

대신 Array.mapi 투영을 사용하여 각 요소와 함께 색인을 조건부로 전달하고 술어를 만족하지 않는 모든 요소를 ​​Array.choose으로 제거 할 수 있습니다.

let arr = [|1.0; 2.0; nan; 2.0; 4.5; nan; nan; 3.0;|] 

arr 
|> Array.mapi (fun i f -> 
    if System.Double.IsNaN f then Some i else None) 
|> Array.choose id 
// val it : int [] = [|2; 5; 6|] 

편집 :

가 또는 당신은 구어체로, f# spec에 따라 array sequence expression, 또는 array comprehension을 활용할 수 있습니다. 이런 종류의 문제에 대해서는 종종 더 간결합니다.

[| for i, f in Array.mapi (fun i f -> i, f) arr do 
    if System.Double.IsNaN f then yield i |] 
// val it : int [] = [|2; 5; 6|] 
+0

고맙습니다 .- 아주 좋습니다. –

관련 문제