What does -> mean in F#?

后端 未结 9 1018
情深已故
情深已故 2020-12-03 02:54

I\'ve been trying to get into F# on and off for a while but I keep getting put off. Why?

Because no matter which \'beginners\' resource I try to look at I see very

相关标签:
9条回答
  • 2020-12-03 03:39

    (a -> b) means "function from a to b". In type annotation, it denotes a function type. For example, f : (int -> String) means that f refers to a function that takes an integer and returns a string. It is also used as a contstructor of such values, as in

    val f : (int -> int) = fun n -> n * 2
    

    which creates a value which is a function from some number n to that same number multiplied by two.

    0 讨论(0)
  • 2020-12-03 03:40

    '->' is not an operator. It appears in the F# syntax in a number of places, and its meaning depends on how it is used as part of a larger construct.

    Inside a type, '->' describes function types as people have described above. For example

    let f : int -> int = ...
    

    says that 'f' is a function that takes an int and returns an int.

    Inside a lambda ("thing that starts with 'fun' keyword"), '->' is syntax that separates the arguments from the body. For example

    fun x y -> x + y + 1
    

    is an expression that defines a two argument function with the given implementation.

    Inside a "match" construct, '->' is syntax that separates patterns from the code that should run if the pattern is matched. For example, in

    match someList with
    | [] -> 0
    | h::t -> 1
    

    the stuff to the left of each '->' are patterns, and the stuff on the right is what happens if the pattern on the left was matched.

    The difficulty in understanding may be rooted in the faulty assumption that '->' is "an operator" with a single meaning. An analogy might be "." in C#, if you have never seen any code before, and try to analyze the "." operator based on looking at "obj.Method" and "3.14" and "System.Collections", you may get very confused, because the symbol has different meanings in different contexts. Once you know enough of the language to recognize these contexts, however, things become clear.

    0 讨论(0)
  • 2020-12-03 03:46

    The nice thing about languages such as Haskell (it's very similar in F#, but I don't know the exact syntax -- this should help you understand ->, though) is that you can apply only parts of the argument, to create curried functions:

    adder n x y = n + x + y
    

    In other words: "give me three things, and I'll add them together". When you throw numbers at it, the compiler will infer the types of n x and y. Say you write

    adder 1 2 3
    

    The type of 1, 2 and 3 is Int. Therefore:

    adder :: Int -> Int -> Int -> Int
    

    That is, give me three integers, and I will become an integer, eventually, or the same thing as saying:

    five :: Int
    five = 5
    

    But, here's the nice part! Try this:

    add5 = adder 5
    

    As you remember, adder takes an int, an int, an int, and gives you back an int. However, that is not the entire truth, as you'll see shortly. In fact, add5 will have this type:

    add5 :: Int -> Int -> Int
    

    It will be as if you have "peeled off" of the integers (the left-most), and glued it directly to the function. Looking closer at the function signature, we notice that the -> are right-associative, i.e.:

    affffder :: Int -> (Int -> (Int -> Int))
    

    This should make it quite clear: when you give adder the first integer, it'll evaluate to whatever's to the right of the first arrow, or:

    add5andtwomore :: Int -> (Int -> Int)
    add5andtwomore = adder 5
    

    Now you can use add5andtwomore instead of "adder 5". This way, you can apply another integer to get (say) "add5and7andonemore":

    add5and7andonemore :: Int -> Int
    add5and7andonemore = adder 5 7
    

    As you see, add5and7andonemore wants exactly another argument, and when you give it one, it will suddenly become an integer!

      > add5and7andonemore 9
     => ((add5andtwomore) 7) 9
     => ((adder 5) 7) 9)
    <=> adder 5 7 9
    

    Substituting the parameters to adder (n x y) for (5 7 9), we get:

      > adder 5 7 9 = 5 + 7 + 9
     => 5 + 7 + 9
     => 21
    

    In fact, plus is also just a function that takes an int and gives you back another int, so the above is really more like:

      > 5 + 7 + 9
     => (+ 5 (+ 7 9))
     => (+ 5 16)
     => 21
    

    There you go!

    0 讨论(0)
提交回复
热议问题