Megjegyzés
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhat bejelentkezni vagy módosítani a címtárat.
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhatja módosítani a címtárat.
Ez az üzenet akkor jelenik meg, ha egy érték olyan típust határoz meg, amely nem egyesül a várt típussal.
Az alábbi kód a hiba egy egyszerű verzióját mutatja be:
let booleanBinding: bool = 10
Ez a kód a következő kimenetet eredményezi:
error FS0001: This expression was expected to have type
'bool'
but here has type
'int'
Itt a típusjegyzetnek booleanBinding kell lennie bool . Az érték 10 azonban a következőre lesz következtetve int: . Mivel int nem ugyanaz, mint boolaz üzenet, ez az üzenet jelenik meg.
Ez az üzenet számos különböző körülmények között adható ki, és mindegyik ugyanazt a mintát követi. A típuskövetkeztetés (vagy a programozó által megadott típusú széljegyzetek) "kijavítják" egy függvény vagy érték típusát egy bizonyos típusra, majd később ezt a típust úgy használják, mintha más típusú lenne, mint a "rögzített" típus. Az alábbi kód a hiba összetettebb verzióját mutatja be, ahol a függvények közötti következtetés azt eredményezi, hogy a hiba messze nem jelenik meg a várttól:
// this function has type `int -> int`.
// `+` takes the type of the arguments passed to it, and `1` is of type `int`, so
// `+` must be of type `int -> int`
let addOne i = i + 1
// this function has type `int -> int`, which may be surprising because no types are explicitly specified.
// the `printfn` call on the first line is of type `'a -> unit`, because `printfn "%A"` takes a value of any type and returns unit.
// this means that the type of the `i` parameter hasn't yet been decided based on how the parameter is used.
// the `addOne` call on the second line is of type `int -> int`, because `addOne` is of type `int -> int` (see above).
// this means that `i` _must_ be of type `int`, so the overall type signature of `printThenAdd` is inferred to be `int -> int`
let printThenAdd i =
printfn "%A" i
addOne i
// this line triggers the error
// > This expression was expected to have type
// > 'int'
// > but here has type
// > 'string'
// because `printThenAdd` has been inferred to have type `int -> int`, but a string was passed in as the `int` parameter
printThenAdd "a number"
|> ignore
Részleges alkalmazás- és típuskövetkeztetés
Egy másik gyakori forgatókönyv, amikor ez a hiba a függvények részleges alkalmazásával jár. Ha több paramétert tartalmazó letfüggvényt határoz meg kötésekkel, az F# lefordított függvényként kezeli. Ez azt jelenti, hogy ha kevesebb argumentumot alkalmaz, mint amennyit a függvény elvár, egy új függvényt ad vissza, amely a fennmaradó argumentumokat várja, ahogyan az az alábbi példában látható:
// Define a function that takes two arguments and returns their sum
let Sum x y = x + y
// This works: RegisterFunction1 accepts a function with generic types 'A -> 'B
// When passed Sum (which is int -> int -> int), type inference maps:
// 'A to int (the first parameter type)
// 'B to int -> int (the remaining function after partial application)
let RegisterFunction1 (fn:'A->'B) = ()
let Test1 = RegisterFunction1 Sum
// This fails: RegisterFunction2 expects a function 'A -> int (returning int, not a function)
// When passed Sum (which is int -> int -> int), type inference maps:
// 'A to int (the first parameter type)
// But then expects the return type to be int, not int -> int (the partially applied function)
let RegisterFunction2 (fn:'A->int) = ()
// Uncommenting the next line would trigger the error:
// > This expression was expected to have type
// > 'int -> int'
// > but here has type
// > 'int -> int -> int'
Ebben a példában Sum egy függvény típusával int -> int -> int. Amikor átadja azt a rendszernek RegisterFunction1, a típuskövető rendszer leképezi 'Aint azokat ( 'Bint -> int a részben alkalmazott függvényt). Amikor azonban megpróbálja átadni azt a (várt) típusrendszernekRegisterFunction2, a típusrendszer helyesen azonosítja a Sum visszaadott int -> int értéket (egy függvényt), nem int pedig az értéket, ami a típuseltérési hibát okozza.'A -> int
További információ arról, hogy az F# hogyan kezeli a függvénydefiníciókat és a részleges alkalmazást, olvassa el a Functionst.
A hiba kijavítása
Az üzenet megoldásához módosítania kell a kötés két részének egyikét: a típusjegyzetet vagy az értékkötést.
Ha az érték helyes, módosítsa vagy távolítsa el a típusjegyzetet.
Ha a típusjegyzet helyes, ellenőrizze a kötött értéket, és győződjön meg arról, hogy nem történt logikai hiba.