Haskell: Show all the elements that are "showable" on a Hlist
Asked Answered
R

2

5

I have tried

map show . mapMaybe fromDynamic $ [toDyn "one", toDyn (\x -> x::Integer), toDyn 3, toDyn ()]

but it returned

["()"]
Ripping answered 4/2, 2013 at 21:22 Comment(3)
Do you really need to store the data mixed up in a list like that?Maugre
You could use a record to store that data much more easily, for example, and you'd easily be able to use functions like show on the elements because the types are available at runtime. Having types fixed at runtime is an advantage, not a disadvantage, so you should do it whenever possible.Maugre
This problem was made up to illustrate my problem. The project I am working is here github.com/rbarreiro/farofias The next step in the project is to add functions, which are not instance of Data.Data.Ripping
A
5

Your code does not do what you expect it to do. Long before the dynamic behaviour of Data.Dynamic kicks in, the Haskell type checker resolves the types. The type of the right part of the expression is

mapMaybe fromDynamic $ [toDyn "one", toDyn (\x -> x::Integer), toDyn 3, toDyn ()] :: Typeable b => [b]

and the type of the left part is

map show :: Show a => [a] -> [String]

so to combine these, the type variable b resp. a gets unified. If you were to compile this from a regular Haskell file, the compiler would give you a warning (The type variable `a' is ambigous). But in GHCi, the interpreter just defaults to ().

But this fixes the type of fromDynamic in the expression to Dynamic -> Maybe (), effectively selecting all elements of type ().

If you force the compiler to use a different type there, e.g. by specifying a type signature, you see that fromDynamic selects a different type:

Prelude Data.Dynamic Data.Maybe> map (show :: Integer -> String) . mapMaybe fromDynamic $ [toDyn "one", toDyn (\x -> x::Integer), toDyn 3, toDyn ()]
["3"]

Unfortunately, there is no way to achieve what you want: Select all elements whose type support a show instance, as that information is not available to fromDynamic.

Annabelannabela answered 4/2, 2013 at 21:36 Comment(0)
H
7

The problem is that fromDynamic must go to a monomorphic type. It is picking (), but with a type signature you could make it pick any other type.

To show it, you would need some function that tries all the possible types in turn. Probably you do not want to store the data like this, but want to store it bundled up with some operations (such as show).

There are two ways you could bundle. My favourite is to have all the functions pre-applied to the value (so for show, you just get a list of thunks of type String).

The other way is to also put the functions into a Dynamic (make sure they are the correct monomorphic type!) and then use dynApply.

Hushaby answered 4/2, 2013 at 21:35 Comment(1)
nice idea: "store it bundled up with some operations"Ripping
A
5

Your code does not do what you expect it to do. Long before the dynamic behaviour of Data.Dynamic kicks in, the Haskell type checker resolves the types. The type of the right part of the expression is

mapMaybe fromDynamic $ [toDyn "one", toDyn (\x -> x::Integer), toDyn 3, toDyn ()] :: Typeable b => [b]

and the type of the left part is

map show :: Show a => [a] -> [String]

so to combine these, the type variable b resp. a gets unified. If you were to compile this from a regular Haskell file, the compiler would give you a warning (The type variable `a' is ambigous). But in GHCi, the interpreter just defaults to ().

But this fixes the type of fromDynamic in the expression to Dynamic -> Maybe (), effectively selecting all elements of type ().

If you force the compiler to use a different type there, e.g. by specifying a type signature, you see that fromDynamic selects a different type:

Prelude Data.Dynamic Data.Maybe> map (show :: Integer -> String) . mapMaybe fromDynamic $ [toDyn "one", toDyn (\x -> x::Integer), toDyn 3, toDyn ()]
["3"]

Unfortunately, there is no way to achieve what you want: Select all elements whose type support a show instance, as that information is not available to fromDynamic.

Annabelannabela answered 4/2, 2013 at 21:36 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.