[Haskell-beginners] newbie: Monad, equivalent notation using Control.Monad.guard

Hugo Ferreira hmf at inescporto.pt
Tue Oct 18 11:52:57 CEST 2011


Hello,

On 10/17/2011 05:22 PM, Brent Yorgey wrote:
> On Mon, Oct 17, 2011 at 04:18:05PM +0100, Hugo Ferreira wrote:
>> Hello,
>>
>> I came across the following code:
>>
>> ngrams'' :: Int ->  [a] ->  [[a]]
>> ngrams'' n l = do
>>    t<- Data.List.tails l
>>    l<- [take n t]
>>    Control.Monad.guard (length l == n)
>>    return l
>>
>> and tried to use the ">>=" operator in order
>> to figure out how Monads work. I came up with:
>>
>> test l =
>>     (Data.List.tails l)
>>     >>= (\t ->  [take 2 t])
>>     >>= (\l ->  if (length l == 2) then [l] else [])
>>
>> Questions:
>> 1. How can I use Control.Monad.guard directly in "test l"
>
> test l =
>      (Data.List.tails l)
>      >>= \t ->  [take 2 t]
>      >>= \l ->  Control.Monad.guard (length l == 2)
>      >>   return l
>
> The rule is that
>
>    x<- foo
>
> desugars to
>
>    foo>>= \x ->  ...
>
> and
>
>    blah
>
> desugars to
>
>    blah>>  ...
>

Ok, I was not aware of the >>.

> One thing that might have been tripping you up is your extra
> parentheses around the lambda expressions.  If you have
>
>    >>= (\l ->  ...)
>    >>   foo...
>
> the l does not scope over foo... so you cannot mention it.  Instead
> what you want is
>
>    >>= \l ->  ...
>    >>   foo...
>
> so the lambda expression is actually   \l ->  ...>>  foo..., that is,
> it includes *everything* after the \l ->  ... and not just the stuff on
> that line.
>

Hmmm. Still cannot wrap my mind around this B-(.

[[1],[2],[3]] >>= \l -> func1 l >>= \m -> func2 m

\l will hold each of the 3 elements of initial list
    these are concatenated with the results of func1
    results in a new list

\m will have each element in the new list
    these are concatenated with the results of func2
    results in a last list

is equal to ?

(([[1],[2],[3]] >>= \l -> func1 l) >>= \m -> func2 m)

Hmmm.. going to lookup more info on this.

>> 2. Related issue: how can create a List monad so that I
>>     can input "l" argument of "test l" directly?
>
> I don't understand this question.  Can you give an example of what you
> are trying to do?
>

Weird. I was trying to execute:

test1' [[1,2,3],[2,3],[3]]

in a version that does not use Data.List.tails
but could not. Now it works. Must have done something
wrong.

Hugo F.


> -Brent
>
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://www.haskell.org/mailman/listinfo/beginners
>




More information about the Beginners mailing list