[GHC] #14367: Lazy evaluation can be invalidated

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Keywords: | Operating System: Unknown/Multiple Architecture: | Type of failure: Other Unknown/Multiple | Test Case: | Blocked By: Blocking: | Related Tickets: Differential Rev(s): | Wiki Page: -------------------------------------+------------------------------------- Evaluating arguments only if and when they are needed. This is the first principle of lazy evaluation.\\ Example:\\ {{{ Prelude> let f True x y = x Prelude> f True 3 (3/0) 3 }}} Good answer! See this:\\ {{{ Prelude> f True 8 undefined 8 }}} and:\\ {{{ Prelude> f True undefined 8 *** Exception: Prelude.undefined CallStack (from HasCallStack): error, called at libraries\base\GHC\Err.hs:79:14 in base:GHC.Err undefined, called at <interactive>:2:8 in interactive:Ghci2 }}} These results are all correct because the evaluated expression (function) is non-strict.\\ The same expression below with a changed argument:\\ {{{ Prelude> f True 3 _ <interactive>:54:10: error: * Found hole: _ :: p20 Where: `p20' is an ambiguous type variable * In the third argument of `f', namely `_' In the expression: f True 3 _ In an equation for `it': it = f True 3 _ * Relevant bindings include it :: p1 (bound at <interactive>:54:1) }}} I understand this error, it is legitimate except that here, in this specific case, I would never use this expression.( i.e{{{_}}}) or the result of that expression if that result were to be used. Here the error message should not have priority. \\ This argument ( i.e {{{_}}}) does not need to be evaluated to calculate the result.\\ With Normal-Order Reduction, an expression is reduced only when absolutely necessary to continue the reduction.\\ So, here, who cares! Since this expression (i.e{{{_}}}), or the result is supposed never to be used.\\ It is the same for this example:\\ {{{ Prelude> f True 3 r <interactive>:55:10: error: Variable not in scope: r }}} Idem, here the error message should not have priority. About {{{r}}} here, who cares! \\ By contrast here in this other example,{{{r}}} must be in the scope to be used:\\ {{{ Prelude> let g x t = x + t + r <interactive>:56:21: error: Variable not in scope: r }}} Anyway,{{{(+)}}} is strict in both arguments.\\ I think leaving the priority to lazy evaluation will bring much more consistency in the results. Of course, ghc would take this error into account and send it after the compilation if needed. \\ These examples are not exaustive examples. See ticket [ticket:14355]. (although in this ticket, the thing is slightly different). -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: closed Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: invalid | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by goldfire): * status: new => closed * resolution: => invalid Comment: It sounds like you want `-fdefer-type-errors` or `-fdefer-typed-holes`. Otherwise, GHC will run only well-typed programs. If you'd like a change in this behavior, please submit a ghc-proposal: that's the only accepted way to suggest a change to GHC's specification. Until then, this ticket is out of scope. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:1 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

It sounds like you want -fdefer-type-errors or -fdefer-typed-holes.\\ Not at all.\\ By this answer it seems that you did not understand, or rather that you do not want to understand. And this is not the first time. Be a
#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: closed Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: invalid | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by vanto): replying to [[span(style=color: #FF0000, goldfire )]]:\\ little more respectful, please. I would prefer a little more reflection on your part, this response to the fast looks like an inconsiderate rejection. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:2 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: closed Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: invalid | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by int-e): There is a curiosity here, IMHO: {{{ GHCi, version 8.2.1: http://www.haskell.org/ghc/ :? for help Prelude> :set -fdefer-typed-holes -Wno-typed-holes Prelude> :set -fdefer-out-of-scope-variables -Wno-deferred-out-of-scope- variables Prelude> let x = [_]; y = [r] Prelude> (length x, length y) (1,1) Prelude> length [_] <interactive>:4:9: error: • Found hole: _ :: a0 Where: ‘a0’ is an ambiguous type variable • In the expression: _ In the first argument of ‘length’, namely ‘[_]’ In the expression: length [_] • Relevant bindings include it :: Int (bound at <interactive>:4:1) Prelude> length [r] 1 }}} Why does the `length [_]` expression produce a compile time error? -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:3 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: closed Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: invalid | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by vanto): replying to [[span(style=color: #FF0000, int-e )]]:\\ Because here it is calculated, so there is an error. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:4 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by vanto): * status: closed => new * resolution: invalid => Comment: Replying to [[span(style=color: #FF0000, goldfire, second time )]]:\\ I reopened this ticket for you to answer.\\ What do you say about that?\\ {{{ Prelude> f True 6 (\x -> ('r'/'u')) <interactive>:4:18: error: * Could not deduce (Fractional Char) arising from a use of `/' from the context: Num p1 bound by the inferred type of it :: Num p1 => p1 at <interactive>:4:1-26 * In the expression: ('r' / 'u') In the third argument of `f', namely `(\ x -> ('r' / 'u'))' In the expression: f True 6 (\ x -> ('r' / 'u')) }}} Who cares! the result must be 6 because of the lazy evaluation.\\ And this:\\ {{{ Prelude> f True 6 (\x -> x+x)1 <interactive>:8:1: error: * Non type-variable argument in the constraint: Num (t1 -> t2) (Use FlexibleContexts to permit this) * When checking the inferred type it :: forall t1 t2. (Num (t1 -> t2), Num t1) => t2 }}} the result must be 6 because of the lazy evaluation too.\\ But here, that run:\\ {{{ Prelude> f True 6 ((\x -> x+x)1) 6 }}} that does not make sense,it should not have an evaluation on the last expression taken into account. \\ some result given by the compiler are '''not coherent,''' but however they are fair because GHC has been coded in this sense. '''Some priorities should be reversed,''' including lazy evaluation and errors. with -fdefer- typed-holes and -fdefer-out-of-scope-variables you answered the problem in part, but not in its entirety.\\ take your time to think about that.\\ do you understand this time? Thanks! -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:5 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

If you'd like a change in this behavior, please submit a ghc-proposal:
Until then, this ticket is out of scope.\\ This is your point of view, not mine because these are ideas that serve for the ticket, like you, when you write your ideas in other tickets. It's
Otherwise, GHC will run only well-typed programs.\\ Yes. Imagine that behind the argument {{{x}}} there are a hundred other expressions? And still imagines there are hundred other functions like
#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by vanto): Replying to [[span(style=color: #FF0000, goldfire, third time )]]:\\ that's the only accepted way to suggest a change to GHC's specification. \\ Yes I know that but you are not interested in what I say, is'nt it? \\ the same thing. \\ this one? This is possible, you do not know! All these expressions must be well typed. And yet they will never be used. They will still be checked by the type inference algorithm. Waste of time! And possible danger thereafter. We do not keep unnecessary things in a program. The type inference algorithm computes, it does not make any decision. And why? Because it was never thought to do this. It would have been better to ask oneself before checking whether the expression or the function to be used is well typed if it will later serve in another function or in another expression.Otherwise what is the use of testing functions or expressions if we know that they will never be used? Since the language exists, has anyone ever thought of that? The type inference can be improved not by calculation but by adding decision making. But that is another matter, is'nt it? -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:6 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

Evaluating arguments only if and when they are needed. This is the first
#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by AntC): Replying to [ticket:14367 vanto]: principle of lazy evaluation.\\
Example:\\ ...\\ These results are all correct because the evaluated expression (function) is non-strict.\\
No, not an accurate statement. Those examples are ''both'' type-correct ''and'' evaluate a non-strict function.
The same expression below with a changed argument:\\ ...\\
That example is not type-correct.
Here the error message should not have priority. \\
Type errors ''always'' "have priority" before evaluating an expression. (Except if you set `-fdefer-type-errors` or `-fdefer-typed-holes`, as @goldfire correctly points out.) GHC is chiefly a compiler, not an interpreter. Haskell is a statically- typed language. Compiled code would be unusable in general if GHC accepted type-incorrect code, then delayed until run-time to see whether it needed to evaluate some type-incorrect expression. Programs would run ok today but crash tomorrow. I think you'll find every statically-typed compiled language behaves like that. It really has nothing to do with lazy evaluation. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:7 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#14367: Lazy evaluation can be invalidated -------------------------------------+------------------------------------- Reporter: vanto | Owner: (none) Type: bug | Status: closed Priority: normal | Milestone: Component: Compiler | Version: 8.2.1 Resolution: invalid | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: Other | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by vanto): * status: new => closed * resolution: => invalid Comment: before closing the ticket here two things:\\ {{{-fdefer-typed-holes}}} and {{{-fdefer-type-errors}}} should not exist in GHC. either an expression is well-typed or it is not well-typed. but you, you invent a "naked" expression that will ultimately still make an error output from the compiler. you hide an existing error for what to do in the end? make the compiler create an error when calculating this expression. that's wonderful! it does not help. It serve no purpose. back to the ticket. Haskell is three main things. lambda-calculus, type inference and lazy evaluation. that's all. in this ticket I point the lazy evaluation. I repeat my question: why give a type to an expression that is known to be unusable by the program?(yes I know why, here it is rather an interrogative sentence). choose between two actions: - it is necessary to give a type to the expression and then to check if it is used.\\ or\\ - it is necessary to check the expression if it is used before giving a type to the expression. \\ We can do it using an identity function, for instance.\\ in both cases the lazy evaluation will not use this expression. Each well-formed expression has, by definition, a value. this value does not work since the expression is not used by the lazy evaluation. this value serve no purpose. I prefer the second action although this does not happen so in GHC. he would probably have thought of that from the beginning. moreover, the lazy evaluation must be given a high priority in relation to the priority of errors or warning.(in this precise case).\\ anyway the type inference has already been changed in the past so why not once again? -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14367#comment:8 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler
participants (1)
-
GHC