
On Thu, Sep 10, 2020 at 11:45:45AM +0500, Ignat Insarov wrote:
Thank you all kind folks who responded.
I think a leap of reasoning has occurred and I would like to ask you all to slow down and notice it.
Record update is special syntax.
It is not a function. It is not as general as a function. It is not perceived nor written as a function. Ain't no lambda in it.
You may say that it desugars to a function. But as a user of the language, I am unconcerned: desugar another way then!
Surely a function of type `C α ⇒ Y α → Y String` may assign different strings to `y`, by consulting methods of `C`. But a record update cannot! Neither the value `y₀` nor the type variable α are ever in the scope of the update expression.
Why do you say it has anything to do with record update being special? The same problem occurs with a true function: Prelude> data Y a = Y { y :: a } Prelude> let defaultY = Y { y = mempty } Prelude> let setYc y = y { y = "c" } Prelude> :t defaultY defaultY :: Monoid a => Y a Prelude> :t setYc setYc :: Y a -> Y [Char] Prelude> :t setYc defaultY <interactive>:1:7: error: • Ambiguous type variable ‘a0’ arising from a use of ‘defaultY’ prevents the constraint ‘(Monoid a0)’ from being solved. Probable fix: use a type annotation to specify what ‘a0’ should be. These potential instances exist: instance Monoid a => Monoid (IO a) -- Defined in ‘GHC.Base’ instance Monoid Ordering -- Defined in ‘GHC.Base’ instance Semigroup a => Monoid (Maybe a) -- Defined in ‘GHC.Base’ ...plus 7 others (use -fprint-potential-instances to see them all) • In the first argument of ‘setYc’, namely ‘defaultY’ In the expression: setYc defaultY