
* Johan Tibell
On Mon, Jan 14, 2013 at 2:57 PM, Roman Cheplyaka
wrote: It's described here: http://hackage.haskell.org/trac/ghc/wiki/NewtypeWrappers
We seem to be talking past each other. There's a specific problem related to type classes and invariants on data types mentioned earlier on this thread. Simon's solution here seems to be that we only coerce a structure from one newtype to the base type if the constructors are exposed, hence my question if the code changes semantics due to adding imports.
Yes, but it is an additional condition. For coercion to be even considered, the coercion function has to be defined somewhere. So Simon's proposal, as I understand it, is to allow compilation of that coercion function only when the relevant data constructors are in scope in the module where the coercion function is defined. In the code you showed in an earlier message, there's no coercion function (just the newtype constructor used as a function), hence the semantics of that code would not change. Here's an example of the code whose compilation would depend on the constructors availability: newtype Age = MkAge Int newtype wrap ageMapWrapper :: Map Int a -> Map Age a f ... = let xs :: Map Int String = ... in ageMapWrapper xs This code is currently impossible to write, if only for the reason that "newtype wrap" is not a valid declaration yet. After the extension is introduced, but before you expose Data.Map.Internal, this code will parse (assuming the relevant extension is turned on) but fail (presumably at the renaming stage) when it is discovered that the coercion requires access to the internal structure of Map. Finally, when you expose Data.Map.Internal, and the author of the above code imports it, the code starts to compile, but the correctness of the Map operations is now contingent on the Age's Ord instance and is the responsibility of the code's author, as we would expect. Roman