Funkce (F#)

Funkce jsou základní jednotkou provádění programu v libovolném programovacím jazyce.Stejně jako v jiných jazycích funkce jazyka F# má název může obsahovat parametry a argumenty vzít a má tělo.F# podporuje také funkční programovacích konstrukcí, jako například replikace funkce jako hodnoty, pomocí nepojmenovaných funkcí ve výrazech, složení funkce k vytvoření nových funkcí, curried funkcí a implicitní definice funkce prostřednictvím částečného aplikaci argumenty funkce.

Definování funkcí pomocí let klíčové slovo, nebo je-li funkce rekurzivní, let rec kombinaci klíčových slov.

// Non-recursive function definition.
let [inline] function-name parameter-list [ : return-type ] = function-body
// Recursive function definition.
let rec function-name parameter-list = recursive-function-body

Poznámky

function-name Je identifikátor, který zastupuje funkci.parameter-list Se skládá z po sobě následujících parametrů, které jsou odděleny mezerami.Explicitní typ pro každý parametr, můžete určit, jak je popsáno v části parametry.Typ konkrétní argument nezadáte, pokusí se kompilátor odvození typu z těla funkce.function-body Se skládá z výrazu.Výraz, který tvoří tělo funkce je obvykle složených výrazů, skládající se z několika výrazy, které v konečné výraz, který je vrácená hodnota případech.return-type Dvojtečky následovaný typu a je volitelné.Pokud explicitně neurčíte typ vrácené hodnoty, že kompilátor určí typ vrácené z konečného výrazu.

Definice jednoduché funkce je podobná následující:

let f x = x + 1

V předchozím příkladu je název funkce f, je argument x, který má typ int, tělo funkce je x + 1, a vrácená hodnota je typu int.

Specifikátor vložené je pokyn kompilátoru, že funkce je malý a kód pro funkci lze integrovat do těla volajícího.

Rozsah

Na libovolné úrovni oboru než je rozsah modulu není chyba znovu použít název hodnota nebo funkce.Pokud jste znovu použít název, název deklarované později stínů název deklarovanou dříve.V oboru nejvyšší úrovně v modulu, musí být jedinečné názvy.Například následující kód vytvoří chybu, když se objeví v oboru modulu, ale ne v případě, že se zobrazí uvnitř funkce:

let list1 = [ 1; 2; 3]
// Error: duplicate definition.
let list1 = []  
let function1 =
   let list1 = [1; 2; 3]
   let list1 = []
   list1

Ale je na libovolné úrovni oboru přijatelné následující kód:

let list1 = [ 1; 2; 3]
let sumPlus x =
// OK: inner list1 hides the outer list1.
   let list1 = [1; 5; 10]  
   x + List.sum list1

Parametry

Názvy parametrů jsou uvedeny za názvem funkce.Typ pro parametr, můžete určit, jak je znázorněno v následujícím příkladu:

let f (x : int) = x + 1

Pokud zadáte typ, následuje název parametru a je oddělený od názvu dvojtečkou.Vynecháte-li typ pro parametr, kompilátor odvodí typ parametru.Například v následující definici funkce argument x je odvozen typ int 1 je typu int.

let f x = x + 1

Avšak kompilátor pokusí vytvořit funkci co nejobecnější.Všimněte si například následující kód:

let f x = (x, x)

Funkce vytvoří n-tice z jeden argument libovolného typu.Protože typ není zadán, funkce lze použít u jakéhokoli typu argumentu.Další informace naleznete v tématu Automatické generalizace (F#).

Funkce orgánů

Tělo funkce mohou obsahovat definice lokální proměnné a funkce.Tyto proměnné a funkce jsou v rozsahu v těle aktuální funkce, ale mimo něj.Je-li povolena možnost zjednodušené syntaxe, je nutné použít odsazení chcete-li označit, že definice v těle funkce, jak je znázorněno v následujícím příkladu:

let cylinderVolume radius length =
    // Define a local value pi.
    let pi = 3.14159
    length * pi * radius * radius

Další informace naleznete v tématu Kód formátování pokyny (F#) a Syntaxe podrobného (F#).

Vrácené hodnoty

Kompilátor používá výsledný výraz v těle funkce k určení návratové hodnoty a typu.Kompilátor může odvodit typ výsledný výraz z předcházejícími výrazy.Ve funkci cylinderVolume, je uvedeno v předchozí části, typ pi se určí na základě typu literál 3.14159 za float.Kompilátor používá typ pi k určení typu výraz h * pi * r * r za float.Proto je celkově návratový typ funkce float.

Návratové hodnoty explicitně specifikovat, zapsat kód následujícím způsobem:


let cylinderVolume radius length : float =
   // Define a local value pi.
   let pi = 3.14159
   length * pi * radius * radius

Kód je napsán nad, kompilátor použije float na celé funkci; Pokud chcete použít typům parametru, použijte následující kód:

let cylinderVolume (radius : float) (length : float) : float

Volání funkce

Volání funkce tak, že zadáte název funkce a mezeru a potom žádné argumenty, které jsou odděleny mezerami.Například volání funkce cylinderVolume a přiřadí výsledek na hodnotu vol, zadejte následující kód:

let vol = cylinderVolume 2.0 3.0

Částečné uplatnění argumenty

Je-li méně než zadaný počet argumentů, vytvořte novou funkci, která očekává, že zbývající argumenty.Tento způsob zpracování argumentů je označována jako currying a je charakteristické pro funkční programovacích jazyků, jako je jazyk F#.Předpokládejme například, pracujete s dvěma velikostmi kanálu: jeden má poloměr 2.0 a druhý má poloměr 3.0.Můžete vytvořit funkce určující objem potrubí takto:

let smallPipeRadius = 2.0
let bigPipeRadius = 3.0

// These define functions that take the length as a remaining
// argument:

let smallPipeVolume = cylinderVolume smallPipeRadius
let bigPipeVolume = cylinderVolume bigPipeRadius

Další argument by potom zadejte podle potřeby různých délek potrubí pro dvě různé velikosti:

let length1 = 30.0
let length2 = 40.0
let smallPipeVol1 = smallPipeVolume length1
let smallPipeVol2 = smallPipeVolume length2
let bigPipeVol1 = bigPipeVolume length1
let bigPipeVol2 = bigPipeVolume length2

Rekurzivní funkce

Rekurzivní funkce jsou funkce, které volají sami.Že vyžadují, aby rec následující klíčové slovo let klíčové slovo.Vyvolání rekurzivní funkci z v těle funkce stejným způsobem, jako by vyvolat žádné volání funkce.Následující rekurzivní funkce počítá ntého Fibonacciho číslo.Fibonacciho číslo sekvence je známo, od antiquity a je pořadí, ve kterém každé následné číslo je součtem s předchozími dvěma čísly posloupnosti.

let rec fib n = if n < 2 then 1 else fib (n - 1) + fib (n - 2)

Některé rekurzivní funkce může být přetečení zásobníku program nebo neefektivního provést v případě, že není je píšete pečlivě a povědomí o speciální techniky, jako je například použití akumulátorů a pokračování.

Hodnoty funkcí

V F# všechny funkce jsou považovány za hodnoty; ve skutečnosti jsou známé jako hodnoty funkce.Funkce jsou hodnoty, a proto bylo možné jako argumenty pro jiné funkce nebo v jiných kontextech kde se používají.Následuje příklad funkci, která přebírá hodnotu funkce jako argument:

let apply1 (transform : int -> int ) y = transform y

Určete typ hodnoty funkce pomocí -> token.Na levé straně tento token je typ argumentu a na pravé straně je návratová hodnota.V předchozím příkladu apply1 je funkce, která má funkci transform jako argument, kde transform je funkce, která trvá celé číslo a vrátí celé číslo, jiné.Následující kód ukazuje, jak používat apply1:

let increment x = x + 1

let result1 = apply1 increment 100

Hodnota result 101 bude po spuštění předchozího kódu.

Více argumenty jsou odděleny po sobě následujících -> tokeny, jak je znázorněno v následujícím příkladu:

let apply2 ( f: int -> int -> int) x y = f x y

let mul x y = x * y

let result2 = apply2 mul 10 20

Výsledkem je 200.

Lambda výrazy

A lambda výraz je nepojmenovaný funkce.V předchozích příkladech namísto definování funkce s názvem increment a mul, můžete použít lambda výrazy takto:

let result3 = apply1 (fun x -> x + 1) 100

let result4 = apply2 (fun x y -> x * y ) 10 20

Definujete pomocí lambda výrazy fun klíčové slovo.Lambda výraz se podobá definici funkce, s výjimkou, že místo = tokenu, -> tokenu slouží k oddělení v seznamu argumentů funkce subjektu.Stejně jako v definici funkce běžné typy argumentů lze odvodit nebo explicitně zadána a návratový typ lambda výraz je odvozen z typu poslední výraz v textu.Další informace naleznete v tématu Lambda výrazy: Fun klíčové slovo (F#).

Funkce složení a použití kanálů

Funkce v F# se může skládat z dalších funkcí.Složení dvě funkce function1 a function2 je jinou funkci, která představuje použití function1 za použití function2:

let function1 x = x + 1
let function2 x = x * 2
let h = function1 >> function2
let result5 = h 100

Výsledkem je 202.

Použití kanálů umožňuje volání funkce být zřetězeno, jako po sobě jdoucích operací.Použití kanálů funguje takto:

let result = 100 |> function1 |> function2

Výsledkem je opět 202.

Operátory složení vezmou dvě funkce a funkce; naopak potrubí operátory funkci a argument a vrátí hodnotu.Následující příklad kódu ukazuje rozdíl mezi hospodářskými subjekty potrubí a složení zobrazením rozdílů v podpisech funkce a využití.

// Function composition and pipeline operators compared.

let addOne x = x + 1
let timesTwo x = 2 * x

// Composition operator
// ( >> ) : ('T1 -> 'T2) -> ('T2 -> 'T3) -> 'T1 -> 'T3
let Compose2 = addOne >> timesTwo

// Backward composition operator
// ( << ) : ('T2 -> 'T3) -> ('T1 -> 'T2) -> 'T1 -> 'T3
let Compose1 = addOne << timesTwo

// Result is 5
let result1 = Compose1 2

// Result is 6
let result2 = Compose2 2

// Pipelining
// Pipeline operator
// ( <| ) : ('T -> 'U) -> 'T -> 'U
let Pipeline1 x = addOne <| timesTwo x

// Backward pipeline operator
// ( |> ) : 'T1 -> ('T1 -> 'U) -> 'U
let Pipeline2 x = addOne x |> timesTwo

// Result is 5
let result3 = Pipeline1 2

// Result is 6
let result4 = Pipeline2 2

Přetížení funkce

Můžete použít přetížení metody typu, ale nikoli funkce.Další informace naleznete v tématu Metody (F#).

Viz také

Další zdroje

Hodnoty (F#)

F# Language Reference