Addition of "Float" and "Int".

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
5 messages Options
Reply | Threaded
Open this post in threaded view
|

Addition of "Float" and "Int".

Venu Chakravorty


Hello everyone,
        I am just starting with Haskell so please bear with me.


Here's my question:


Consider the below definition / output:


Prelude> :t (+)
(+) :: (Num a) => a -> a -> a


        What I understand from the above is that "+" is a function that takes two args
which are types of anything that IS-AN instance of "Num" (Int, Integer, Float, Double)
and returns an instance of "Num".
Hence this works fine:
Prelude> 4.3 + 2
6.3


But I can't understand why this doesn't work:
Prelude> 4.3 + 4 :: Int


<interactive>:1:0:
    No instance for (Fractional Int)
      arising from the literal `4.3' at <interactive>:1:0-2
    Possible fix: add an instance declaration for (Fractional Int)
    In the first argument of `(+)', namely `4.3'
    In the expression: 4.3 + 4 :: Int
    In the definition of `it': it = 4.3 + 4 :: Int


        I expected that the second addition would work as both "Float" and "Int" are
instances of "Num". Is it that since both the formal args are defined as "a" they
have to be exactly the same instances? Had "+" been defined something like:
(+) :: (Num a, Num b) => a -> b -> a
my second addition would have worked?


Please let me know what I am missing.


Regards,
Venu Chakravorty.

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.haskell.org/pipermail/beginners/attachments/20140512/dcef70bb/attachment.html>

Reply | Threaded
Open this post in threaded view
|

Addition of "Float" and "Int".

Brandon Allbery
On Mon, May 12, 2014 at 11:44 AM, Venu Chakravorty <c.venu at aol.com> wrote:

> Prelude> :t (+)
> (+) :: (Num a) => a -> a -> a
>
>  What I understand from the above is that "+" is a function that takes
> two args
> which are types of anything that IS-AN instance of "Num" (Int, Integer,
> Float, Double)
> and returns an instance of "Num".
>

Not exactly. It says that, given some type a that is an instance of Num, it
will add two values of that type and produce a new value of that same type.
You cannot mix and match types; it always works on some specific type,
although those types may change between uses of (+).

This is somewhat hidden by the way numeric literals are handled: a literal
without a decimal point is handled as if you had wrapped it in
fromIntegral, and one with a decimal point is handled as if you had wrapped
it in fromRational.

--
brandon s allbery kf8nh                               sine nomine associates
allbery.b at gmail.com                                  ballbery at sinenomine.net
unix, openafs, kerberos, infrastructure, xmonad        http://sinenomine.net
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.haskell.org/pipermail/beginners/attachments/20140512/bcffd5f6/attachment.html>

Reply | Threaded
Open this post in threaded view
|

Addition of "Float" and "Int".

Mateusz Kowalczyk
In reply to this post by Venu Chakravorty
On 05/12/2014 05:44 PM, Venu Chakravorty wrote:

>
>
> Hello everyone,
> I am just starting with Haskell so please bear with me.
>
>
> Here's my question:
>
>
> Consider the below definition / output:
>
>
> Prelude> :t (+)
> (+) :: (Num a) => a -> a -> a
>
>
> What I understand from the above is that "+" is a function that takes two args
> which are types of anything that IS-AN instance of "Num" (Int, Integer, Float, Double)
> and returns an instance of "Num".
> Hence this works fine:
> Prelude> 4.3 + 2
> 6.3
>
>
> But I can't understand why this doesn't work:
> Prelude> 4.3 + 4 :: Int
>
>
> <interactive>:1:0:
>     No instance for (Fractional Int)
>       arising from the literal `4.3' at <interactive>:1:0-2
>     Possible fix: add an instance declaration for (Fractional Int)
>     In the first argument of `(+)', namely `4.3'
>     In the expression: 4.3 + 4 :: Int
>     In the definition of `it': it = 4.3 + 4 :: Int
>
>
> I expected that the second addition would work as both "Float" and "Int" are
> instances of "Num". Is it that since both the formal args are defined as "a" they
> have to be exactly the same instances? Had "+" been defined something like:
> (+) :: (Num a, Num b) => a -> b -> a
> my second addition would have worked?
>

Just to follow up on the part Brandon didn't explain, no, (Num a, Num b)
=> a -> b -> a would not work either: there is not enough information
there to do anything sensible. That is, we don't know how to turn any
arbitrary Num into any other arbitrary Num.

What if it was (4 :: Int) + (7.5 :: Double). The type signature would
match but the result is fractional and we promised to return Int.

This is the reason why it's Num a => a -> a -> a; we only know how to
add things of the same type together. If we want more, we need to have
more information.

> Please let me know what I am missing.
>
>
> Regards,
> Venu Chakravorty.
>
>
>
>
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://www.haskell.org/mailman/listinfo/beginners
>


--
Mateusz K.

Reply | Threaded
Open this post in threaded view
|

Addition of "Float" and "Int".

Sylvain HENRY
In reply to this post by Venu Chakravorty
>Is it that since both the formal args are defined as "a" they have to be
exactly the same instances?

Exactly.

>Had "+" been defined something like: (+) :: (Num a, Num b) => a -> b -> a
> my second addition would have worked?

Yes except that you cannot write this function given the definition of Num
http://hackage.haskell.org/package/base-4.7.0.0/docs/Prelude.html#t:Num

If you want your second example to work, you have to explicitly convert the
floating-point value into an Int (using floor, ceiling or round for
instance).

-Sylvain


2014-05-12 17:44 GMT+02:00 Venu Chakravorty <c.venu at aol.com>:

>   Hello everyone,
>  I am just starting with Haskell so please bear with me.
>
>  Here's my question:
>
>  Consider the below definition / output:
>
>  Prelude> :t (+)
> (+) :: (Num a) => a -> a -> a
>
>  What I understand from the above is that "+" is a function that takes
> two args
> which are types of anything that IS-AN instance of "Num" (Int, Integer,
> Float, Double)
> and returns an instance of "Num".
> Hence this works fine:
> Prelude> 4.3 + 2
> 6.3
>
>  But I can't understand why this doesn't work:
> Prelude> 4.3 + 4 :: Int
>
>  <interactive>:1:0:
>     No instance for (Fractional Int)
>       arising from the literal `4.3' at <interactive>:1:0-2
>     Possible fix: add an instance declaration for (Fractional Int)
>     In the first argument of `(+)', namely `4.3'
>     In the expression: 4.3 + 4 :: Int
>     In the definition of `it': it = 4.3 + 4 :: Int
>
>  I expected that the second addition would work as both "Float" and "Int"
> are
> instances of "Num". Is it that since both the formal args are defined as
> "a" they
> have to be exactly the same instances? Had "+" been defined something
> like:
> (+) :: (Num a, Num b) => a -> b -> a
> my second addition would have worked?
>
>  Please let me know what I am missing.
>
>  Regards,
> Venu Chakravorty.
>
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://www.haskell.org/mailman/listinfo/beginners
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.haskell.org/pipermail/beginners/attachments/20140514/f14df198/attachment.html>

Reply | Threaded
Open this post in threaded view
|

Addition of "Float" and "Int".

MJ Williams
In reply to this post by Mateusz Kowalczyk
I'm sure someone else on this list will explain it much more
eloquently than I, but for now, here goes:
What you are effectively forcing haskell to do is to return a result
that hasn't been defined.  You can't force a result of type `Int'
where `+' has not been defined to return such a result for the sum of
a Float(s) and integers(s).  Of course, in languages such as C you
can use casting for the purpose, but we are talking about very
different, in fact, entirely different programming paradigms.

hth,
Matthew
At 00:17 14/05/2014, you wrote:

>On 05/12/2014 05:44 PM, Venu Chakravorty wrote:
> >
> >
> > Hello everyone,
> >       I am just starting with Haskell so please bear with me.
> >
> >
> > Here's my question:
> >
> >
> > Consider the below definition / output:
> >
> >
> > Prelude> :t (+)
> > (+) :: (Num a) => a -> a -> a
> >
> >
> >       What I understand from the above is that "+" is a function
> that takes two args
> > which are types of anything that IS-AN instance of "Num" (Int,
> Integer, Float, Double)
> > and returns an instance of "Num".
> > Hence this works fine:
> > Prelude> 4.3 + 2
> > 6.3
> >
> >
> > But I can't understand why this doesn't work:
> > Prelude> 4.3 + 4 :: Int
> >
> >
> > <interactive>:1:0:
> >     No instance for (Fractional Int)
> >       arising from the literal `4.3' at <interactive>:1:0-2
> >     Possible fix: add an instance declaration for (Fractional Int)
> >     In the first argument of `(+)', namely `4.3'
> >     In the expression: 4.3 + 4 :: Int
> >     In the definition of `it': it = 4.3 + 4 :: Int
> >
> >
> >       I expected that the second addition would work as both
> "Float" and "Int" are
> > instances of "Num". Is it that since both the formal args are
> defined as "a" they
> > have to be exactly the same instances? Had "+" been defined
> something like:
> > (+) :: (Num a, Num b) => a -> b -> a
> > my second addition would have worked?
> >
>
>Just to follow up on the part Brandon didn't explain, no, (Num a, Num b)
>=> a -> b -> a would not work either: there is not enough information
>there to do anything sensible. That is, we don't know how to turn any
>arbitrary Num into any other arbitrary Num.
>
>What if it was (4 :: Int) + (7.5 :: Double). The type signature would
>match but the result is fractional and we promised to return Int.
>
>This is the reason why it's Num a => a -> a -> a; we only know how to
>add things of the same type together. If we want more, we need to have
>more information.
>
> > Please let me know what I am missing.
> >
> >
> > Regards,
> > Venu Chakravorty.
> >
> >
> >
> >
> > _______________________________________________
> > Beginners mailing list
> > Beginners at haskell.org
> > http://www.haskell.org/mailman/listinfo/beginners
> >
>
>
>--
>Mateusz K.
>_______________________________________________
>Beginners mailing list
>Beginners at haskell.org
>http://www.haskell.org/mailman/listinfo/beginners