Why haskell doesn't have heterogeneous lists

I do not understand why I cannot create a list that looks like [1,"1",1.1] in haskell. I don’t think that this is a static typing, which interferes because I thought that head would now have a poorly defined type, but then I thought about it, and there is no reason for the runtime system to not instantiate a different version of head every time when a list is entered into it, so head [1,"1",1.1] will be typed as List->Int and head (tail [1,"1",1.1]) will be typed as List->String . Since runtime already does a lot of accounting, why doesn't it provide more spectacular polymorphic (or are it common) versions of various foreplay functions? What am I missing here?

+4
source share
5 answers

In fact, it is a typification that prevents this. Consider the definition of a list (note the type parameter a , which is not in your types):

 data List a = Nil | Cons a (List a) 

In Cons a (List a) you can see that the type of the item at the head of the list should be of the same type as the elements that follow it. To answer your question, you won’t miss a lot: as you say, runtime can do this, but in Haskell you want to make these input decisions at compile time, not runtime.

If you need heterogeneous lists, you can see some kind of magic of Oleg Kiselev in his work on HList (= Heterogeneous list). It may not be exactly what you want, but it is in the same rough direction.

+16
source

Because in Haskell, all types are known at compile time. There is no such thing as waiting for execution time to find out what type will be. And because this is enough to do everything that you might want to do in a dynamically typed system, but it’s easier to talk about loading.

+3
source

Just to let you know, there really is a package for heterogeneous lists using non-trivial methods, and you really need to make sure you understand the type system well before diving into it. You do not have this by default due to the type system. A list in Haskell is not just a list. This is a list of a, 'a', which is Int, String, whatever you want. BUT, one list can contain only one type of value.

Note that you can define “heterogeneous lists” of elements that satisfy some constraints using existential quantification, but I think you are not there yet and should really focus on understanding the other answers here before moving on.

+3
source

There is a heterogeneous list type of HList (available on Hackage), but note that there is probably a content type of your list. Consider something like this:

 history = [-12, "STATEMENT END", (-244, time January 4 2010), ...] 

Your data has a type trying to appear, for example:

 data HistoryEntry = Withdrawal Int | StatementClosing | ScheduledPayment Int CalendarTime history = [Withdrawal 12, StatementClosing, ScheduledPayment 244 (time January 4 2010)] 

In many cases, your data is of the type that you just need to look for.

+3
source

See Heterogeneous Collections

 {-# OPTIONS -fglasgow-exts #-} -- -- An existential type encapsulating types that can be Shown -- The interface to the type is held in the show method dictionary -- -- Create your own typeclass for packing up other interfaces -- data Showable = forall a . Show a => MkShowable a -- -- And a nice existential builder -- pack :: Show a => a -> Showable pack = MkShowable -- -- A heteoregenous list of Showable values -- hlist :: [Showable] hlist = [ pack 3 , pack 'x' , pack pi , pack "string" , pack (Just ()) ] -- -- The only thing we can do to Showable values is show them -- main :: IO () main = print $ map f hlist where f (MkShowable a) = show a {- *Main> main ["3","'x'","3.141592653589793","\"string\"","Just ()"] -} 
+3
source

Source: https://habr.com/ru/post/1334313/


All Articles