2017-07-28 13 views
4

私はF#の初心者です。F#タイプと関数のシグネチャ

私はほとんど同じ(座標とベクトル)の2種類があります。このタイプの推論のために、適切に動作することができず、それぞれの関数に正しい型を指定するのに苦労します。

それは何とかそれはここでベクトルですundestand:

type Coordinate = {X:int; Y:int} 
type Vector = {X:int; Y:int} 

let calculateVector (origin:Coordinate) (destination:Coordinate) = { X=destination.X-origin.X; Y= destination.Y-origin.Y;} 

そして、ここで私がコーディネートの戻り値の型をしたいとき、私は、この関数の戻り値にそれを指定する方法を見つけることができません。

let calculateNextCoordinate (coordinate:Coordinate) direction = 
    match direction with 
    | "N" -> { X=coordinate.X; Y=coordinate.Y-1 } 
    | "NE" -> { X=coordinate.X+1; Y=coordinate.Y-1 } 
    | "E" -> { X=coordinate.X+1; Y=coordinate.Y } 
    | "SE" -> { X=coordinate.X+1; Y=coordinate.Y+1 } 
    | "S" -> { X=coordinate.X; Y=coordinate.Y+1 } 
    | "SW" -> { X=coordinate.X-1; Y=coordinate.Y+1 } 
    | "W" -> { X=coordinate.X-1; Y=coordinate.Y } 
    | "NW" -> { X=coordinate.X-1; Y=coordinate.Y-1 } 
    | _ -> coordinate 

デフォルトのケースでこのエラーが発生しました:この表現には 'Vector'が必要ですが、ここに 'Coordinate'タイプがあります。

私は疲れては関数シグネチャのためにこのウェブサイト上の外観を持っているが、私の問題のために何ができませんでした:https://fsharpforfunandprofit.com/posts/function-signatures/

質問:

どのようにこのエラーを修正するのですか?

推論型は、デフォルトでは、(私の例のVectorでは)プロパティに一致する最後の型を宣言しているからですか?

ボーナス:F#でこのような状況を処理するより良い方法はありますか?

{ X = 2; Y = 3} 

あなたはベクトルと座標間の命名の競合を作成:レコードは、そのメンバー名を使用して構築されているので、事前

答えて

6

感謝。 F#では、コンパイラはそのような場合に常に最新の定義に解決します。したがって、あなたの例では、コンパイラはレコード{X = ...、Y = ...}をベクトルとして解釈します。

F# records on fsharpforfunandprofit.comには良い記事があります。これは簡単にこれを処理する方法を説明しています。これは良い説明を読むことをお勧めします。

しかし、短期的には、レコードタイプを持つレコードインスタンスのメンバーのいずれかの前に付けることができます。

{ Coordinate.X = 2; Y = 3 } // Creates a Coordinate 
{ X = 2; Coordinate.Y = 3 } // Creates a Coordinate 

{ Vector.X = 2; Y = 3 } // creates a vector 
+0

私が探していたまさにおかげで、とのリンクは本当に良いです。 –

関連する問題