Sök…


Omvändning av en lista av vilken typ som helst

För att vända en lista är det inte viktigt vilken typ av listelementen är, bara vilken ordning de är i. Detta är en perfekt kandidat för en generisk funktion, så samma omvänd funktion kan användas oavsett vilken lista som ges.

let rev list =
    let rec loop acc = function
        | []           -> acc
        | head :: tail -> loop (head :: acc) tail
    loop [] list

Koden gör inga antaganden om elementens typer. Kompilatorn (eller F # interaktiv) berättar att typsignaturen för denna funktion är 'T list -> 'T list . 'T säger att det är en generisk typ utan begränsningar. Du kanske också ser 'a istället för 'T - brevet är obetydligt eftersom det bara är en generisk platshållare. Vi kan passera en int list eller en string list , och båda kommer att fungera framgångsrikt, returnera en int list respektive en string list .

Till exempel i F # interaktiv:

> let rev list = ...
val it : 'T list -> 'T list
> rev [1; 2; 3; 4];;
val it : int list = [4; 3; 2; 1]
> rev ["one", "two", "three"];;
val it : string list = ["three", "two", "one"]

Kartlägga en lista till en annan typ

let map f list =
    let rec loop acc = function
        | []           -> List.rev acc
        | head :: tail -> loop (f head :: acc) tail
    loop [] list

Signaturen för denna funktion är ('a -> 'b) -> 'a list -> 'b list , som är den mest generiska den kan vara. Detta förhindrar inte att 'a är av samma typ som att vara 'b , men det tillåter dem också att vara annorlunda. Här kan du se att 'a typ som är den parameter till funktionen f måste matcha typen av list parameter. Den här funktionen är fortfarande generisk, men det finns vissa små begränsningar på ingångarna - om typerna inte matchar kommer det att finnas ett kompileringsfel.

Exempel:

> let map f list = ...
val it : ('a -> 'b) -> 'a list -> 'b list
> map (fun x -> float x * 1.5) [1; 2; 3; 4];;
val it : float list = [1.5; 3.0; 4.5; 6.0]
> map (sprintf "abc%.1f") [1.5; 3.0; 4.5; 6.0];;
val it : string list = ["abc1.5"; "abc3.0"; "abc4.5"; "abc6.0"]
> map (fun x -> x + 1) [1.0; 2.0; 3.0];;
error FS0001: The type 'float' does not match the type 'int'


Modified text is an extract of the original Stack Overflow Documentation
Licensierat under CC BY-SA 3.0
Inte anslutet till Stack Overflow