Personal tools

User:Zzo38/Proposal for instance disambiguation

From HaskellWiki

Jump to: navigation, search

This document has some of my ideas about instance disambiguations and related things how it could be implemented in Haskell. There may be some mistake, so it is good for other people complain what is wrong so that it can be corrected.

1 Select instances from imported modules


import A () instance ();
import B class (AAA as ZZZ qualified as HHH);
import C hiding instance (Num String, Num Bool);
import D type (T as TT, U as newtype UU);

From module A imports nothing not even instances. From module B imports instances of class AAA to be instances of class ZZZ instead, where all its methods are prefixed with "HHH." at the front. From module C, does not import instances of Num class for type String (this is only valid if type synonym instances is enabled, and means the same thing here) and Bool. From module D, the type named T is named TT when imported, for all functions using it, all instances, etc. If T is a type from a different module, then all function and instance from D using type T will make a new type TT instead. Instances for the type U are instead for a new type UU which is U wrapped in a newtype.

2 Override instances


import E hiding module C;

This hides instances in C which conflict with those of E, and hides names (except qualified)


instance Num Int where {
  x + y = 42;

This, defined in a module, automatically overrides instances from imported modules.


instance (instance IsString [Char] hiding) => IsString [x];

It means that this is instance for any list but if there is instance for strings, that one will override this one.


instance Num x => Monoid (x as newtype (Sum x)) where {
  mempty = 0;
  mappend = (+);

Allows you to define newtype as part of an instance declaration, doing wrapping and unwrapping automatically.

3 Instance with imported modules

In general, you override instance, it doesn't affect functions from imported modules that use their own instances internally. However, there is some cases of overriding (this example requires scoped type variables):

module Example where {
  value1 :: Int;
  value1 = 2 + 3;
  value2 :: (Num x, x ~ Int) => x;
  value2 = ((+) :: x -> x -> x) 2 3;
module Main where {
  import Example;
  instance Num Int where {
    _ + _ = 42;
  main = print (value1, value2);

The result will be:

(5, 42)