title: List of showables OOP-style in Haskell?
body: <p>I want to build a list of different things which have one property in common, namely, they could be turned into string. The object-oriented approach is straightforward: define interface <code>Showable</code> and make classes of interest implement it. Second point can in principle be a problem when you can't alter the classes, but let's pretend this is not the case. Then you create a list of <code>Showable</code>s and fill it with objects of these classes without any additional noise (e.g. upcasting is usually done implicitly). Proof of concept in Java <a href="https://ideone.com/ogyJVe" rel="nofollow noreferrer">is given here</a>.</p>
  
  <p>My question is what options for this do I have in Haskell? Below I discuss approaches that I've tried and which don't really satisfy me.</p>
  
  <p><strong>Approach 1</strong>: existensials. Works but ugly.</p>
  
  <pre><code>{-# LANGUAGE ExistentialQuantification #-}
  data Showable = forall a. Show a =&gt; Sh a
  
  aList :: [Showable]
  aList = [Sh (1 :: Int), Sh "abc"]
  </code></pre>
  
  <p>The main drawback for me here is the necessity for <code>Sh</code> when filling the list. This closely resembles upcast operations which are implicitly done in OO-languages.</p>
  
  <p>More generally, the dummy wrapper <code>Showable</code> for the thing which is already in the language — <code>Show</code> type class — adds extra noise in my code. No good.</p>
  
  <p><strong>Approach 2</strong>: impredicatives. Desired but does not work.</p>
  
  <p>The most straightforward type for such a list for me and what I really desire would be:</p>
  
  <pre><code>{-# LANGUAGE ImpredicativeTypes #-}
  aList :: [forall a. Show a =&gt; a]
  aList = [(1 :: Int), "abc"]
  </code></pre>
  
  <p>Besides that (<a href="https://jozefg.bitbucket.io/posts/2014-12-23-impredicative.html" rel="nofollow noreferrer">as I heard</a>)<code>ImpredicativeTypes</code> is “fragile at best and broken at worst”
  it does not compile:</p>
  
  <pre><code>Couldn't match expected type ‘a’ with actual type ‘Int’
    ‘a’ is a rigid type variable bound by
        a type expected by the context: Show a =&gt; a
  </code></pre>
  
  <p>and the same error for <code>"abc"</code>. (Note type signature for 1: without it I receive even more weird message: <code>Could not deduce (Num a) arising from the literal ‘1’</code>).</p>
  
  <p><strong>Approach 3</strong>: Rank-N types together with some sort of functional lists (difference lists?).</p>
  
  <p>Instead of problematic <code>ImpredicativeTypes</code> one would probably prefer more stable and wide-accepted <code>RankNTypes</code>. This basically means: move 
  desired <code>forall a. Show a =&gt; a</code> out of type constructor (i.e. <code>[]</code>) to plain function types. Consequently we need some representation of lists as plain functions. As I barely heard there are such representations. The one I heard of is difference lists. But in <a href="http://hackage.haskell.org/package/dlist-0.7.1.2/docs/Data-DList.html" rel="nofollow noreferrer"><code>Dlist</code> package</a> the main type is good old <code>data</code> so we return to impredicatives. I didn't investigate this line any further as I suspect that it could yield more verbose code than in approach 1. But if you think it won't, please give me an example.</p>
  
  <p><strong>Bottom line</strong>: how would you attack such a task in Haskell? Could you give more succinct solution than in OO-language (especially in place of filling a list — see comment for code in approach 1)? Can you comment on how relevant are the approaches listed above?</p>
  
  <p><strong>UPD</strong> (based on first comments): the question is of course simplified for the purpose of readability. The real problem is more about how to store things which share the same type class, i.e. can be processed later on in a number of ways (<code>Show</code> has only one method, but other classes can have more than one). This factors out solutions which suggest apply <code>show</code> method right when filling a list.</p>