4

行ベクトルの配列として行列を表す配列Pの配列があり(この表現は私の目的にとってより便利です)、その配列の列ベクトルjを抽出したいと思います。私の最初のパスは:

let column (M: float[][]) (j: int) =
   Array.map(fun v -> v.[j]) M

これはコンパイルに失敗し、v。[j]が不確定なタイプのオブジェクトに対して演算子expr。[idx]を使用していることを示しています。vにカーソルを合わせると、vがfloat []として認識されるため、これは私には不可解です。これは行ベクトルであると私は信じています。

さらに、次のコードが機能します。

let column (M: float[][]) (j: int) =
   Array.map(fun v -> v) M
   |> Array.map (fun v -> v.[j])

2番目の例が最初の例とどのように違うのか理解できません。2番目の例の最初のマップは冗長に見えます。配列をそれ自体にマッピングしていますが、これで型決定の問題が解決したようです。

私が間違っていることや見ないことを理解する助けがあれば大歓迎です!

4

2 に答える 2

6

問題は、コンパイラが認識できるように、F# の型推論が厳密に左から右であることです。

let column (M: float[][]) (j: int) =
   Array.map(fun v -> v.[j]) 

この時点では、それについてまったく何も知らないvため、エラーがスローされます。これが、前方パイプ演算子|>が非常に一般的である理由です-コードを次のように書き換えます

let column (M: float[][]) (j: int) =
   M |> Array.map(fun v -> v.[j]) 

結構です。これが、2番目の例が機能する理由でもあります

于 2012-05-24T04:39:19.653 に答える
3

型チェッカーは左から右に動作するため、型 ofvは特定されていませんが、型 ofMは後で利用可能になります。したがって:

let column (M: float[][]) (j: int) =
   M |> Array.map (fun v -> v.[j])

また

let column M (j: int) =
   Array.map (fun (v: float []) -> v.[j]) M

動作します。

2 番目の例でfun v -> vは、どのタイプでも問題ありません。したがって、配列要素の型に問題はありません。の 2 番目の部分は|>期待どおりに機能し、パイプ演算子を使用する必要があるもう 1 つのポイントを示しています。

于 2012-05-24T04:50:09.210 に答える