Send Beginners mailing list submissions to
        [email protected]

To subscribe or unsubscribe via the World Wide Web, visit
        http://www.haskell.org/mailman/listinfo/beginners
or, via email, send a message with subject or body 'help' to
        [email protected]

You can reach the person managing the list at
        [email protected]

When replying, please edit your Subject line so it is more specific
than "Re: Contents of Beginners digest..."


Today's Topics:

   1. Re:  Convert String to List/Array of Numbers (Felipe Lessa)
   2. Re:  Convert String to List/Array of Numbers (Daniel Fischer)
   3. Re:  Convert String to List/Array of Numbers (Brent Yorgey)
   4. Re:  [OT] To Mock A Mockingbird (Michael Vanier)


----------------------------------------------------------------------

Message: 1
Date: Wed, 8 Sep 2010 10:40:39 -0300
From: Felipe Lessa <[email protected]>
Subject: Re: [Haskell-beginners] Convert String to List/Array of
        Numbers
To: Lorenzo Isella <[email protected]>
Cc: [email protected]
Message-ID:
        <[email protected]>
Content-Type: text/plain; charset=UTF-8

On Wed, Sep 8, 2010 at 10:31 AM, Lorenzo Isella
<[email protected]> wrote:
> in the interactive shell and get a string, but I am having
> problems in converting this to a list or anything more
> manageable (where every entry is an integer number
> i.e. something which can be summed, subtracted etc...). Ideally
> even a list where every entry is a row (a list in itself) would
> do.

Well, first of all you can split your input into lists using

    lines :: String -> [String]

Then, you can split each line into columns by using

    words :: String -> [String]

Now, on each of these columns you can convert to an integer by
using:

    read :: Read a => String -> a

So in the end, you'll end up with something of type [[Int]].


Does this help you to go into the right direction?

Cheers! =)

PS: Yes, that link's information sort of applies, but you'll be
handling lists of lists (i.e. rows of columns).

--
Felipe.


------------------------------

Message: 2
Date: Wed, 8 Sep 2010 16:06:22 +0200
From: Daniel Fischer <[email protected]>
Subject: Re: [Haskell-beginners] Convert String to List/Array of
        Numbers
To: [email protected]
Cc: Lorenzo Isella <[email protected]>
Message-ID: <[email protected]>
Content-Type: text/plain;  charset="iso-8859-1"

On Wednesday 08 September 2010 15:31:19, Lorenzo Isella wrote:
> Dear All,
> I must be stuck on something pretty basic (I am struggling badly with
> I/O). Let us assume you have a rather simple file mydata.dat (3 columns
> of integer numbers), see below.
>
>
>
> 1246191122 1336 1337
> 1246191142 1336 1337
> 1246191162 1336 1337
> 1246191182 1336 1337
> 1246191202 1336 1337
> 1246191222 1336 1337
> 1246191242 1336 1337
> 1246191262 1336 1337
> 1246191282 1336 1337
> 1246191302 1336 1337
> 1246191322 1336 1337
> 1246191342 1336 1337
> 1246191362 1336 1337
> 1246191382 1336 1337
> 1246191402 1336 1337
> 1246191422 1336 1337
>
> Now, my intended pipeline could be
>
> read file as string--> convert to list of integers-->pass it to hmatrix
> (or try to convert it into a matrix/array).
> Leaving aside the last step, I can easily do something like
>
> let dat=readFile "mydata.dat"
>
>
> in the interactive shell and get a string,

Not quite. `dat' is the IO-action that reads the file, of type (IO String) 
and not a String.
In a programme, you'd do something like

main = do
    ... -- argument parsing perhaps
    txt <- readFile "mydata.dat"
    let dat = convert txt
    doSomething with dat

> but I am having problems in
> converting this to a list or anything more manageable (where every entry
> is an integer number i.e. something which can be summed, subtracted
> etc...). Ideally even a list where every entry is a row (a list in
> itself) would do.

Depending on what the reult type should be, different solutions are 
required.
The simplest solutions for such a file format are built from

read  -- to convert e.g. "135" to 135
lines :: String -> [String]
words :: String -> [String]
map :: (a -> b) -> [a] -> [b]

If you want a flat list of Integers from that file,

convert = map read . words

will do. First, `words' splits the String on whitespace (spaces and 
newlines), producing a list of digit-strings, those are then read as 
Integers.

If you want a list of lists, each line its own list inside the top level 
list,

convert = map (map read . words) . lines

is what you want.

If you want to convert each line into a different data structure, say 
(Integer, Double, Int64), the general form would still be

convert = map parseLine . lines

and parseLine would depend on the structure you want. For the above,

parseLine str
    = case words str of
        (a : b : c : _) -> (read a, read b, read c)
        _ -> error "Bad line format"

would be a solution.

For any but the simplest formats, you should write a real parser to deal 
with possible bad formatting though (writing parsers is fun in Haskell).

> I found online this suggestion
> http://bit.ly/9jv1WG
> but I am not sure if it really applies to this case.
> Many thanks
>
> Lorenzo



------------------------------

Message: 3
Date: Wed, 8 Sep 2010 10:07:01 -0400
From: Brent Yorgey <[email protected]>
Subject: Re: [Haskell-beginners] Convert String to List/Array of
        Numbers
To: [email protected]
Message-ID: <[email protected]>
Content-Type: text/plain; charset=us-ascii

On Wed, Sep 08, 2010 at 03:31:19PM +0200, Lorenzo Isella wrote:
> Now, my intended pipeline could be
> 
> read file as string--> convert to list of integers-->pass it to
> hmatrix (or try to convert it into a matrix/array).
> Leaving aside the last step, I can easily do something like
> 
> let dat=readFile "mydata.dat"
> 
> 
> in the interactive shell and get a string, but I am having problems

Note, this may be a bit misleading!  The interactive shell does some
special handling of things involving I/O.  The type of readFile
"mydata.dat" is

  readFile "mydata.dat" :: IO String

That is, an *I/O operation which, when performed*, will yield a String.
This is not at all the same thing as having a String!  In order to get
your hands on the String, you will want to do something like this:

  do dat <- readFile "mydata.dat"    -- dat :: String
     let mat = parseMat dat
     ... do other stuff with mat ...

  parseMat :: String -> [[Integer]]
  parseMat = ...

You may want to read

  http://www.haskell.org/haskellwiki/Introduction_to_IO

or, really, any good Haskell tutorial (e.g. LYAH [1] or RWH [2]) will
cover this.

-Brent

[1] http://learnyouahaskell.com/
[2] http://book.realworldhaskell.org/


------------------------------

Message: 4
Date: Wed, 08 Sep 2010 08:03:36 -0700
From: Michael Vanier <[email protected]>
Subject: Re: [Haskell-beginners] [OT] To Mock A Mockingbird
To: Patrick LeBoutillier <[email protected]>
Cc: beginners <[email protected]>
Message-ID: <[email protected]>
Content-Type: text/plain; charset=ISO-8859-1; format=flowed

  On 9/8/10 4:57 AM, Patrick LeBoutillier wrote:
> Hi all,
>
> I've been reading the book "To Mock A Mockingbird" by Robert Smullyan
> recently and I don't get the part about the birds at all. I think I
> understand that a bird is a function, but what would it's type be in
> Haskell?
>
> It says that birds hear a call and answer by another call, so I
> thought String ->  String or something like that. But if you have a
> mockingbird that can answer what a bird would answer to itself, that
> means that it's input must contain the other bird... Do all the birds
> have the same type?
>
>
> Thanks,
>
> Patrick
>
Patrick,

It's a cool book, well worth reading.  A bird is a function of a single 
argument, which must be another bird, and it returns yet another bird.  
So the only kind of data are functions of a single argument which return 
the same kinds of functions.  This is called "combinatory logic" (CL), 
and is equivalent to what's called untyped lambda calculus (LC).  CL 
terms can be converted to LC terms and vice-versa.  Haskell itself is 
based on a system similar to LC (but much richer), and not all of the 
terms in CL can be written in Haskell.  You can play with them in ghci:

ghci> let i x = x
ghci> :t i
i :: forall t: t -> t
ghci> let k x y = x
ghci> :t k
k :: forall t t1. t -> t1 -> t
ghci> let s x y z = (x z) (y z)
ghci> :t s
s :: forall t t1 t2. (t -> t1 -> t2) -> (t -> t1) -> t -> t2

s, k, and i are three basic combinators.  In fact, you can get i from s 
and k:

ghci> let i2 = s k k
ghci> :t i2
i2 :: forall t. t -> t

i and i2 are the identity function (called "id" in Haskell).  k is 
called "const" in Haskell.  s is a generalized function application 
function.

However, some simple combinations of s, k, and i can't be typed in Haskell:

ghci> :t s i i
<interactive>:1:4:
     Occurs check: cannot construct the infinite type: t1 = t1 -> t2
     Probable cause: `i' is applied to too few arguments
     In the second argument of `s', namely `i'
     In the expression: s i i

That's because (s i i) is equivalent to this function:

ghci> let m z = z z

This is Smullyan's Mockingbird function.  Haskell doesn't allow 
functions with so-called "infinite types" like this, even though they 
can be useful (Haskell provides other ways to get what infinite types 
would give you).

There is a long, fascinating road ahead of you if you decide to continue 
studying this material :-)

Mike




------------------------------

_______________________________________________
Beginners mailing list
[email protected]
http://www.haskell.org/mailman/listinfo/beginners


End of Beginners Digest, Vol 27, Issue 19
*****************************************

Reply via email to