tags:

views:

759

answers:

3

I have a haskell function that that calculates the size of the list of finite Ints. I need the output type to be an Integer because the value will actually be larger than the maximum bound of Int (the result will be -1 to be exact if the output type is an Int)

size :: a -> Integer
size a =  (maxBound::Int) - (minBound::Int)

I understand the difference between Ints (bounded) and Integers (unbounded) but I'd like to make an Integer from an Int. I was wondering if there was a function like fromInteger, that will allow me to convert an Int to an Integer type.

+5  A: 

You'll need to convert the values to Integers, which can be done by the fromIntegral function (numeric casting for Haskell):

fromIntegral :: (Integral a, Num b) => a -> b

It converts any type in the Integral class to any type in the (larger) Num class. E.g.

fromIntegral (maxBound::Int) - fromIntegral (minBound::Int)

However, I would not really trust the approach you're taking -- it seems very fragile. The behaviour in the presence of types that admit wraparound is pretty suspect.

What do you really mean by: "the size of the list of finite Ints". What is the size in this sense, if it isn't the length of the list?

Don Stewart
@dons: your expression previously yielded the `Integer` `-1`. I edited your answer so it yields `0xff..` (hope you don't mind)
yairchu
Yes it is in essence the length of the list, but even a finite list may be large. So to get the length of a list, I would need to first construct the list then interate over it. This way I can just produce the answer without generating the entire list :)
Fry
+3  A: 

I believe you are looking for:

fromIntegral :: (Integral a, Num b) => a -> b

which will convert an Integer to an Int

Rouan van Dalen
...and vice-versa.(i.e. convert an Int into an Integer)
BMeph
A: 

Perhaps you were assuming that Haskell, like many main-stream languages like C and (to a certain extent) Java, has implicit numeric coercions. It doesn't: Int and Integer are totally unrelated types and there is a special function for converting between them: fromIntegral. It belongs to the Num typeclass. Look at the documentation: essentially, fromIntegral does more than that: it is a generic "construct the representation of an arbitrary integral number", t.i. if you're implementing some kind of numbers and instantiating Num, you must provide a way to construct integral numbers of your type. For example, in the Num instance for complex numbers, fromIntegral creates a complex number with a zero imaginary part and an integral real part.

The only sense in which Haskell has implicit numeric coercions is that integer literals are overloaded, and when you write 42, the compiler implicitly interprets it as "fromIntegral (42::Integer)", so you can use integers in whatever contexts where a Num type is required.

jkff
Sorry to be a nitpicker (but since it touches one of my peeves about the Num class "stack", I will indulge...) but since the `Complex a` type (what, not a class? Is that one of those "premature optimizations?) has a `RealFloat a` context, your fromIntegral'd Complex number will not have an integral real part, but a "Real" one, most likely a Double.Other than that little quibble, that's a pretty good answer - carry on!
BMeph