Converting numbers
Converting between numerical types in haskell must be done explicitly, this is unlike languages like C which automatically cast between numerical types in certain situations.
Integral types
Integral types are ones which may only contain whole numbers and not fractions such as Int
and Integer
in the standard haskell libraries.
The workhorse is fromIntegral
which will convert any integral type into another.
Rational types
toRational
fromRational
Going back and forth
Integral type to rational type
toRational
Rational to Integral
Ihis is inherently a lossy transformation since integral types cannot express non-whole numbers. Depending on how you wish to convert, you might choose one of several methods.
ceiling
floor
truncate
round
original
Hi, I am trying to write some funs that convert between two coordinate systems. The first coordinate system, which ill call coord1, starts in the upper left at (0, 0) and ends in the lower right at (500, 500). Coordinates in coord1 have type (Int, Int). The second coord system, which ill call coord2, starts in the lower left at (0.0, 0.0) and ends in the upper right at (1.0, 1.0). Coords in coord2 have type (Float, Float). I was hoping someone could help me figure out how I can rewrite the two functions below so that the type checker will accept them.
coord1ToCoord2 :: (Int, Int) -> (Float, Float)
coord1ToCoord2 (x, y) = (x/500, (500-y)/500)
coord2ToCoord1 :: (Float, Float) -> (Int, Int)
coord2ToCoord1 (x, y) = (500/(1/x), 500 - 500/(1/y))
examples of what i want. i think i have the logic right :)
coord1ToCoord2 (0, 0) -> (0.0, 1.0)
coord1ToCoord2 (250, 250) -> (0.5, 0.5)
coord1ToCoord2 (350, 350) -> (0.7, 0.3)
coord1ToCoord2 (500, 500) -> (1.0, 0.0)
coord2ToCoord1 (0.0, 0.0) -> (0, 500)
coord2ToCoord1 (0.5, 0.5) -> (250, 250)
coord2ToCoord1 (0.7, 0.7) -> (350, 150)
coord2ToCoord1 (1.0, 1.0) -> (500, 0)
Ah. I realize what is messing me up.
When i saw an expression like
500 * 0.2
i had assumed that 500 :: Integer because it didnt end in a .0. but it actually has type Double. so my problem was i would do something like this
(toInteger (500 :: Int)) * 0.2
which of course the typechecker wouldnt accept. now that i have rid myself of my incorrect assumptions i see that i should be writing
(fromRational (toRational (500 :: Int)) * 0.2) :: Float
now that i have a better understanding i am able to write my funs. thank you for your help :)
Automatic conversion
Repeatedly people ask for automatic conversion between numbers. Refer to the thoughts about a Generic number type.