Большинство материалов F # действительно объясняют, что все операторы верхнего уровня в модуле выполняются сверху вниз при объявлении. Другими словами, то, что вы объявили, является не функцией, а значением, которое связывается один раз при запуске программы.
Это действительно помогает увидеть отраженный код. У меня есть простой файл:
let juliet = "awesome"
let juliet2() = "awesome"
Скомпилированный код выглядит примерно так:
public static string juliet
{
[CompilerGenerated, DebuggerNonUserCode]
get
{
return "awesome";
}
}
//...
public static string juliet2()
{
return "awesome";
}
То есть одно является статическим свойством, а другое - функцией. Это желательное свойство, потому что представьте, если бы у нас было что-то вроде этого:
let x = someLongRunningDatabaseCall()
Мы хотим, чтобы x
был связан только один раз, мы не хотим, чтобы он вызывал функцию базы данных каждый раз, когда мы получаем доступ к x
.
Кроме того, мы можем написать интересный код, подобный этому:
> let isInNebraska =
printfn "Creating cities set"
let cities = set ["Omaha"; "Bellevue"; "Lincoln"; "Papillion"; "La Vista"; "Ralston"]
fun n -> cities.Contains(n);;
Creating cities set
val isInNebraska : (string -> bool)
> isInNebraska "Omaha";;
val it : bool = true
> isInNebraska "Okaloosa";;
val it : bool = false
Поскольку isInNebraska
является значением, оно оценивается немедленно. Просто так получилось, что его тип данных (string -> bool)
, поэтому он выглядит как функция. В результате мы заполняем наш cities
набор только один раз, даже если мы вызываем функцию 1000 раз.
Давайте сравним этот код с этим:
> let isInNebraska2 n =
printfn "Creating cities set"
let cities = set ["Omaha"; "Bellevue"; "Lincoln"; "Papillion"; "La Vista"; "Ralston"]
cities.Contains(n);;
val isInNebraska2 : string -> bool
> isInNebraska2 "Omaha";;
Creating cities set
val it : bool = true
> isInNebraska2 "Okaloosa";;
Creating cities set
val it : bool = false
Упс, мы создаем новые города, установленные каждый раз, когда мы вызываем функцию.
Таким образом, между ценностями и функциями определенно существует законное и реальное различие.