let 束縛

"バインド" は、識別子を値または関数に関連付けます。 名前を値または関数にバインドするには、let キーワードを使用します。

構文

// Binding a value:
let identifier-or-pattern [: type] =expressionbody-expression
// Binding a function value:
let identifier parameter-list [: return-type ] =expressionbody-expression

解説

let キーワードは、1 つまたは複数の名前に対する値または関数値を定義するために、バインド式で使用されます。 let 式の最も単純な形式では、次のように単純な値に名前がバインドされます。

let i = 1

改行を使用して識別子から式を分離する場合は、次のコードのように、式の各行をインデントする必要があります。

let someVeryLongIdentifier =
    // Note indentation below.
    3 * 4 + 5 * 6

次のコードに示すように、名前だけでなく、名前を含むパターンを指定することもできます (タプルなど)。

let i, j, k = (1, 2, 3)

"本体式" は、名前が使用される式です。 本体式は、独自の行に記述し、let キーワード内の最初の文字と正確に一致するようにインデントします。

let result =

    let i, j, k = (1, 2, 3)

    // Body expression:
    i + 2 * j + 3 * k

let バインドは、モジュール レベル、クラス型の定義、またはローカル スコープ (関数定義など) で使用できます。 モジュール内の最上位レベルまたはクラス型の let バインドは、本体式を持つ必要はありませんが、その他のスコープ レベルでは、本体式が必要です。 次のコードに示すように、バインドされた名前は定義の時点より後で使用できますが、let バインドが出現するより前の時点では使用できません。

// Error:
printfn "%d" x
let x = 100
// OK:
printfn "%d" x

関数のバインド

次のコードに示すように、関数のバインドは、関数名とパラメーターが含まれている点を除けば、値のバインドの規則に従います。

let function1 a = a + 1

一般に、パラメーターはタプル パターンなどのパターンです。

let function2 (a, b) = a + b

let バインド式は、最後の式の値として評価されます。 したがって、次のコード例では、result の値は 100 * function3 (1, 2) から計算され、300 と評価されます。

let result =
    let function3 (a, b) = a + b
    100 * function3 (1, 2)

詳細については、「関数」を参照してください。

型の注釈

パラメーターの型を指定するには、コロン (:) を追加してその後で型名を指定し、すべてをかっこで囲みます。 戻り値の型を指定するには、最後のパラメーターの後にコロンと型を追加します。 パラメーターの型として整数を使用する function1 の完全な型の注釈は、次のようになります。

let function1 (a: int) : int = a + 1

明示的な型パラメーターがない場合は、型の推定を使用して、関数のパラメーターの型が決定されます。 これには、パラメーターの型のジェネリックへの自動的なジェネリック化が含まれます。

詳細については、「自動ジェネリック化」と「型推論」を参照してください。

クラス内の let 束縛

let バインドはクラス型では使用できますが、構造体またはレコード型では使用できません。 クラス型で let バインドを使用するには、クラスにプライマリ コンストラクターが必要です。 コンストラクターのパラメーターは、クラス定義の型名の後に記述する必要があります。 クラス型の let バインドにより、そのクラス型のプライベート フィールドとメンバーが定義され、型の do バインドと共に、型のプライマリ コンストラクターのコードを形成します。 次のコード例では、クラス MyClass とプライベート フィールド field1 および field2 を示します。

type MyClass(a) =
    let field1 = a
    let field2 = "text"
    do printfn "%d %s" field1 field2
    member this.F input =
        printfn "Field1 %d Field2 %s Input %A" field1 field2 input

field1field2 のスコープは、それらが宣言されている型に制限されます。 詳細については、「クラス内の let 束縛」と「クラス」を参照してください。

let バインドの型パラメーター

モジュール レベル、型、またはコンピュテーション式内の let バインドには、明示的な型パラメーターを指定できます。 関数定義内などの式の let バインドには、型パラメーターを指定できません。 詳細については、「ジェネリック」を参照してください。

let バインドの属性

次のコードに示すように、モジュールの最上位の let バインドには、属性を適用できます。

[<Obsolete>]
let function1 x y = x + y

let バインドのスコープとアクセス可能性

let バインドを使用して宣言されたエンティティのスコープは、バインドが出現した後の、それを含むスコープ (関数、モジュール、ファイル、クラスなど) の部分に限定されます。 そのため、let バインドによって名前がスコープに導入される、ということができます。 モジュールでは、モジュール内の let バインドはモジュールのパブリック関数にコンパイルされるため、モジュールがアクセス可能であれば、モジュールのクライアントは let バインドされた値または関数にアクセスできます。 これに対し、クラス内の let バインドはクラスに対してプライベートです。

通常、モジュール内の関数をクライアント コードで使用するときは、モジュールの名前で修飾する必要があります。 たとえば、モジュール Module1 に関数 function1 がある場合、ユーザーが関数を参照するには Module1.function1 と指定します。

モジュールのユーザーは、インポート宣言を使用することにより、そのモジュール内の関数を、モジュール名で修飾することなく使用できるようにすることができます。 前述の例では、モジュールのユーザーは、その場合、インポート宣言 open Module1 を使用してモジュールを開くことができ、その後、function1 を直接参照できます。

module Module1 =
    let function1 x = x + 1.0

module Module2 =
    let function2 x =
        Module1.function1 x

open Module1

let function3 x =
    function1 x

一部のモジュールには RequireQualifiedAccess 属性があります。これは、それによって公開される関数を、モジュールの名前で修飾する必要があることを意味します。 たとえば、F# の List モジュールにはこの属性があります。

モジュールとアクセス制御の詳細については、「 モジュール」と「アクセス制御」を参照してください。

関連項目