What is the difference between . (dot) and $ (dollar sign)?

后端 未结 13 2057
庸人自扰
庸人自扰 2020-11-22 04:57

What is the difference between the dot (.) and the dollar sign ($)?

As I understand it, they are both syntactic sugar for not needing to us

13条回答
  •  暖寄归人
    2020-11-22 05:13

    Haskell: difference between . (dot) and $ (dollar sign)

    What is the difference between the dot (.) and the dollar sign ($)?. As I understand it, they are both syntactic sugar for not needing to use parentheses.

    They are not syntactic sugar for not needing to use parentheses - they are functions, - infixed, thus we may call them operators.

    Compose, (.), and when to use it.

    (.) is the compose function. So

    result = (f . g) x
    

    is the same as building a function that passes the result of its argument passed to g on to f.

    h = \x -> f (g x)
    result = h x
    

    Use (.) when you don't have the arguments available to pass to the functions you wish to compose.

    Right associative apply, ($), and when to use it

    ($) is a right-associative apply function with low binding precedence. So it merely calculates the things to the right of it first. Thus,

    result = f $ g x
    

    is the same as this, procedurally (which matters since Haskell is evaluated lazily, it will begin to evaluate f first):

    h = f
    g_x = g x
    result = h g_x
    

    or more concisely:

    result = f (g x)
    

    Use ($) when you have all the variables to evaluate before you apply the preceding function to the result.

    We can see this by reading the source for each function.

    Read the Source

    Here's the source for (.):

    -- | Function composition.
    {-# INLINE (.) #-}
    -- Make sure it has TWO args only on the left, so that it inlines
    -- when applied to two functions, even if there is no final argument
    (.)    :: (b -> c) -> (a -> b) -> a -> c
    (.) f g = \x -> f (g x)
    

    And here's the source for ($):

    -- | Application operator.  This operator is redundant, since ordinary
    -- application @(f x)@ means the same as @(f '$' x)@. However, '$' has
    -- low, right-associative binding precedence, so it sometimes allows
    -- parentheses to be omitted; for example:
    --
    -- >     f $ g $ h x  =  f (g (h x))
    --
    -- It is also useful in higher-order situations, such as @'map' ('$' 0) xs@,
    -- or @'Data.List.zipWith' ('$') fs xs@.
    {-# INLINE ($) #-}
    ($)                     :: (a -> b) -> a -> b
    f $ x                   =  f x
    

    Conclusion

    Use composition when you do not need to immediately evaluate the function. Maybe you want to pass the function that results from composition to another function.

    Use application when you are supplying all arguments for full evaluation.

    So for our example, it would be semantically preferable to do

    f $ g x
    

    when we have x (or rather, g's arguments), and do:

    f . g
    

    when we don't.

提交回复
热议问题