Re: [Haskell-cafe] class and instance

2011-07-10 Thread Brandon Allbery
On Sun, Jul 10, 2011 at 06:49, Patrick Browne patrick.bro...@dit.ie wrote:
 My main question is in understanding the relationship between the
 arguments of the functions getX and getY in the class and in the
 instance. It seems to me that the constructor Pt 1 2 produces one
 element of type Point which has two components. How does this square
 with the class definition of getX which has two arguments?

One argument.  But your main confusion is between the data constructor
which takes two arguments, and the type constructor which takes one.

Point a -- type constructor, takes a type a and produces a new type Point a
Pt a a  -- data constructor, takes two values of some type a and
produces a new value of type Point a

Type constructors are used in type signatures; data constructors are
used in code.  You can't use Pt a a as a type; it's a (polymorphic)
value.  Conversely, you can't use Point a as a value (that is, foo
(Point a) is an error, because foo requires a value, not a type).

-- 
brandon s allbery                                      allber...@gmail.com
wandering unix systems administrator (available)     (412) 475-9364 vm/sms

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] class and instance

2011-07-10 Thread Steffen Schuldenzucker

On 07/10/2011 12:49 PM, Patrick Browne wrote:

Hi,
I am trying to understand the following code.
I have written my current (mis-)understanding and questions below.
I do not wish to improve the code, it is from a research paper[1] that I
am trying to understand.

Pat
[1] ftp://ftp.geoinfo.tuwien.ac.at/medak/phdmedak.pdf

-- A specification. The class Points takes two type variables.
-- The functions take variables of type p, a; return a value of type a.


No. The class 'Points' takes two type variables, 'p' of kind (* - *) 
(that is, p is a type constructor: it can be applied to a type, yielding 
a type), and 'a' of kind *.
Then 'p a' is a type and getX, getY take /one/ argument respectively, of 
this type.



  class Points p a where
   getX :: p a -  a
   getY :: p a -  a

-- A parameterized representation
-- One constructor takes two elements of type a and produces a Point.
  data Point a = Pt a a

-- An implementation of the class Points on the data type (Point a)


Actually, it's an implementation (we say instance) of the class Points 
for the type constructor 'Point' and any type 'a'.



-- In  Pt b c constructor the variables b and c areboth of type a.
-- The type a is left undefined until evaluation


I would say 'arbitrary' instead of 'undefined': The code below says that 
for any type of your choice, which we call 'a', you get an instance 
Points Point a.



  instance Points Point a where
   getX (Pt b c) = b
   getY (Pt b c) = c

-- This runs with any type e.g. Integers
-- getX(Pt 1 2)
-- :t getX(Pt 1 2)
-- getX(Pt 1 2) :: forall t. (Num t) =  t


My main question is in understanding the relationship between the
arguments of the functions getX and getY in the class and in the
instance. It seems to me that the constructor Pt 1 2 produces one
element of type Point which has two components. How does this square
with the class definition of getX which has two arguments?
Is there a difference between:
getX :: p a -  a
  and
getX :: p -  a -  a


Yes, the first version takes one argument of type 'p a', and the second 
takes two of types 'p' and 'a'. See above. This seemed to be you main issue.


As a last note, if you always have instances like the one above, where 
the second parameter is arbitrary, your definition of the class 'Points' 
could be simplified to


 class Points p where
   -- forall a is added implicitly.
   getX :: p a - a
   getY :: p a - a

 instance Points Point where
   -- copy'n'paste from above

-- Steffen

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] class and instance

2011-07-10 Thread Daniel Schoepe
On Sun, 10 Jul 2011 11:49:44 +0100, Patrick Browne patrick.bro...@dit.ie 
wrote:
 My main question is in understanding the relationship between the
 arguments of the functions getX and getY in the class and in the
 instance. It seems to me that the constructor Pt 1 2 produces one
 element of type Point which has two components. How does this square
 with the class definition of getX which has two arguments?
 Is there a difference between:
 getX :: p a - a

This applies the type constructor p, in this case Point to the type
variable a. It is not a function that takes two arguments.

A minor clarification: Pt 1 2 produces a value of type (Num a) = Point
a, so a type where the type constructor Point is already applied to
something. Just Point is not a valid type a value can have, but
something that you have to apply to another type, called a type
constructor.

  and
 getX :: p - a - a

This is a function that takes two arguments.

Cheers,
Daniel


pgpHx4UHpkIaI.pgp
Description: PGP signature
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Class and Instance

2011-06-11 Thread Patrick Browne
Thanks for the feedback. I have two further questions
1. Why is it that the Containers class signature does not allow
instances to be list of list? I suspect it is because x is a constructor.
2. How would I change the Containers  class signature to allow instances
to be lists of lists.

Thanks,
Pat

-- x is a type constructor, not a type
class  Containers x y where
 insert :: y - x y - x y
 remove :: y - x y - x y
 whatsIn :: x y - [y]


instance Containers [] Char where
 insert y [] = y:[]
 insert y m  = y:m
 remove _ [] = []
 remove x (y:ys) | x == y= remove x ys
 | otherwise = y : remove x ys
 whatsIn  = id


instance Containers [] Integer where
 insert y [] = y:[]
 insert y m  = y:m
 remove _ [] = []
 remove x (y:ys) | x == y= remove x ys
 | otherwise = y : remove x ys

 whatsIn  = id

-- cannot have containers of containers.
-- instance Containers [] [] where
-- container.hs:41:23:
--`[]' is not applied to enough type arguments
--  Expected kind `*', but `[]' has kind `* - *'
--  In the instance declaration for `Containers [] []'
-- Failed, modules loaded: none.

This message has been scanned for content and viruses by the DIT Information 
Services E-Mail Scanning Service, and is believed to be clean. http://www.dit.ie

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Class and Instance

2011-06-11 Thread Daniel Patterson
The problem is that [] alone is not a concrete type - that is what the error is 
saying, that [] needs to be applied to another type to yield a concrete type. 
IE, you need a list of something, not just the idea of a list. That something 
can be polymorphic, so the following works (note the [a]):

class  Containers x y where
  insert :: y - x y - x y
  {-remove :: y - x y - x y
  whatsIn :: x y - [y]-}

instance Containers [] [a] where
  insert x y = x:y
  


On Jun 11, 2011, at 5:49 AM, Patrick Browne wrote:

 Thanks for the feedback. I have two further questions
 1. Why is it that the Containers class signature does not allow
 instances to be list of list? I suspect it is because x is a constructor.
 2. How would I change the Containers  class signature to allow instances
 to be lists of lists.
 
 Thanks,
 Pat
 
 -- x is a type constructor, not a type
 class  Containers x y where
 insert :: y - x y - x y
 remove :: y - x y - x y
 whatsIn :: x y - [y]
 
 
 instance Containers [] Char where
 insert y [] = y:[]
 insert y m  = y:m
 remove _ [] = []
 remove x (y:ys) | x == y= remove x ys
 | otherwise = y : remove x ys
 whatsIn  = id
 
 
 instance Containers [] Integer where
 insert y [] = y:[]
 insert y m  = y:m
 remove _ [] = []
 remove x (y:ys) | x == y= remove x ys
 | otherwise = y : remove x ys
 
 whatsIn  = id
 
 -- cannot have containers of containers.
 -- instance Containers [] [] where
 -- container.hs:41:23:
 --`[]' is not applied to enough type arguments
 --  Expected kind `*', but `[]' has kind `* - *'
 --  In the instance declaration for `Containers [] []'
 -- Failed, modules loaded: none.
 
 This message has been scanned for content and viruses by the DIT Information 
 Services E-Mail Scanning Service, and is believed to be clean. 
 http://www.dit.ie
 
 ___
 Haskell-Cafe mailing list
 Haskell-Cafe@haskell.org
 http://www.haskell.org/mailman/listinfo/haskell-cafe


___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Class and Instance

2011-06-10 Thread Daniel Schoepe
On Fri, 10 Jun 2011 17:28:22 +0100, Patrick Browne patrick.bro...@dit.ie 
wrote:
 -- Not OK
 -- insert 2 [9,2]

This causes an error, because numeric literals like 2 are polymorphic:

 :t 2
2 :: Num a = a

If you fix the type to Integer, it works as expected:

insert (2 :: Integer) [9,2]

By the way: It's helpful to include the error messages in your mail when
some piece of code doesn't compile.

Cheers,
Daniel


pgpiVLpuLW0ar.pgp
Description: PGP signature
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Class and Instance

2011-06-10 Thread Yves Parès
You can also modify you class if your intent is that it always work with
polymorph types (And it will save you some trouble with functional
dependencies between types x and y. Plus, it will be Haskell98 compliant)

-- insert, remove and whatsIn are then supposed to work *forall y*, and then
impose the kind of x to be * - * (x is a type constructor, not a mere type)
class Container x where
insert :: y - x y - x y
remove :: y - x y - x y
whatsIn :: x y - [y]

Then you can do:
import Data.List (delete)

instance Container [] where
insert = (:)
remove = delete  -- removes only the first occurence
-- remove x = filter (/= x)  -- if you want to remove *every* occurence
of x (there may be a better way)
whatsIn = id


2011/6/10 Patrick Browne patrick.bro...@dit.ie

 Hi
 Below is a class that I wish to create some instances of.
 I do not wish to change the class definition.
 It is supposed to represent containers of type x that contain things of
 type y.

 My attempt at the insert function seems ok for Char and lists, but not
 ok for Integer. How do I instantiate this class for integers and lists?

 Does this class definition permit y to be a list and hence x to be a
 list of lists? Something like: instance Containers [] [] where ..

 Is this a constructor class?

 Thanks,
 Pat


 class  Containers x y where
  insert :: y - x y - x y
  remove :: y - x y - x y
  whatsIn :: x y - [y]

 instance Containers [] Char where
  insert y [] = y:[]
  insert y m  = y:m


 instance Containers [] Integer where
  insert y [] = y:[]
  insert y m  = y:m


 -- OK
 -- insert  '1' ['u','u','l','i']

 -- Not OK
 -- insert 2 [9,2]

 This message has been scanned for content and viruses by the DIT
 Information Services E-Mail Scanning Service, and is believed to be clean.
 http://www.dit.ie

 ___
 Haskell-Cafe mailing list
 Haskell-Cafe@haskell.org
 http://www.haskell.org/mailman/listinfo/haskell-cafe

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe