<  February 2017   >
Su Mo Tu We Th Fr Sa  
          1  2  3  4  
 5  6  7  8  9 10 11  
12 13 14 15 16 17 18  
19 20 21 22 23 24 25  
26 27 28
00:00 bydo joined
00:03 louispan joined
00:03 bruschkov joined
00:03 Apocalisp joined
00:13 greglearns joined
00:13 greglearns joined
00:14 jle` joined
00:15 Apocalis_ joined
00:17 greglearns joined
00:19 kmelva joined
00:19 louispan joined
00:25 cschneid_ joined
00:33 ghostcard joined
00:40 <Jannoo> i have a quick question
00:40 <Jannoo> in the following: data Date =
00:40 <Jannoo> Date DayOfWeek Int
00:41 <Jannoo> what does the second "Date" after the "=" mean
00:44 <Cale> Jannoo: That's the name of the new data constructor you're introducing
00:44 <Cale> Jannoo: The first occurrence of Data is the name of the new type (constructor) you're introducing
00:45 <Cale> They live in separate namespaces, so they can have the same name
00:45 <Cale> The data constructor will be a function Date :: DayOfWeek -> Int -> Date
00:46 <geekosaur> Haskell uses data constructors to track the type of an expression (literals like 1 and 'c' are conceptually no different from data Integer = ... | -1 | 0 | 1 | ..., even if you can't write that)
00:47 <Jannoo> so its a type called "Date" and the values that can live it in are "Date x y" where x is values that live in DayOfWeek and y is values that live in Int?
00:49 oconnorct1 joined
00:49 <Cale> Jannoo: yes
00:49 <Jannoo> got it
00:49 IRCFrEAK joined
00:49 IRCFrEAK left
00:49 <Jannoo> so whenever a date value is typed out at the term level, it must start with "Date "
00:50 <Jannoo> ?
00:51 greglearns joined
00:51 <kmelva> Jannoo: yeah, to construct the value of type Date, you must use the function Date... if that's what you're asking
00:51 abhiroop joined
00:51 <Jannoo> aaah
00:52 <Jannoo> thanks kmelva Cale and geekosaur
00:52 <kmelva> Jannoo: you can alias it, in away... if you write `makeMeADate = Date` you can use `makeMeADate` now... :)
00:52 louispan joined
00:52 <Jannoo> a tangential question, why don't i need to type out "Num 1" when im typing out the number 1 in REPL
00:53 <Jannoo> type inference?
00:53 <geekosaur> that was what I was trying to get at with my comment
00:53 <geekosaur> (a) Num is not a type, it's a typeclass (if you haven't gotten to those yet, think: interface)
00:54 <geekosaur> (b) things like 1 are actually a bit weird because Haskell turns them into functions (!)
00:54 <geekosaur> :t 1
00:54 <lambdabot> Num t => t
00:54 <geekosaur> (c) but something like 'c' is a fixed type, not much different from data MyType = Ta | Tb | Tc | ...
00:55 <geekosaur> (that is, the Char literal 'c')
00:55 <geekosaur> it acts like a constructor with no parameters, the same way Nothing or True does
00:56 <Jannoo> i think i got it. thanks again geekosaur
00:57 <Jannoo> you guys roc
00:57 <Jannoo> k
00:57 <Jannoo> back to it :)
01:02 greglearns joined
01:03 malaclyps joined
01:04 bruschkov joined
01:06 chlong joined
01:07 NoCreativity joined
01:07 harfangk joined
01:09 louispan joined
01:17 NoCreativity joined
01:20 MotherFlojo joined
01:21 <Jannoo> heres another one, how does Haskell know that the last "==" is not referring to the first "==" in: instance Eq a => Eq (Identity a) where (==) (Identity v) (Identity v') = v == v'
01:22 <benzrf> Jannoo: the types are different
01:22 abhiroop joined
01:22 <benzrf> v, v' :: a, so it uses the instance for a, not for Identity a
01:24 <Jannoo> aaah, thanks benzrf
01:25 <benzrf> np
01:27 cschneid_ joined
01:28 takle joined
01:32 olivierw joined
01:35 Majiir joined
01:36 takle joined
01:40 flounders joined
01:40 Youmu joined
01:45 takle joined
01:51 gfixler joined
01:51 malaclyps joined
01:58 takle joined
01:58 Foras joined
02:01 harfangk joined
02:02 justinfokes joined
02:04 conal joined
02:05 takle joined
02:06 bruschkov joined
02:06 contiver joined
02:06 begriffs joined
02:07 conal joined
02:08 jamie_ joined
02:10 ghostcard joined
02:13 xektor joined
02:16 contiver_ joined
02:16 conal joined
02:16 Rodya_ joined
02:17 conal joined
02:17 xektor joined
02:17 Xektor_ joined
02:18 takle joined
02:19 tom7942 joined
02:20 staffehn joined
02:23 abhiroop joined
02:29 conal joined
02:30 tom7942 joined
02:31 mjs2600 joined
02:39 haskman joined
02:43 takle joined
02:46 justinfokes joined
02:49 hphuoc25 joined
02:50 haskman joined
02:52 haskman joined
02:53 abhiroop joined
02:55 ghostcard joined
02:56 conal joined
02:59 yaewa joined
03:07 tom7942 joined
03:07 bruschkov joined
03:07 takle joined
03:11 conal joined
03:12 hexagoxel_ joined
03:13 conal joined
03:13 takle joined
03:17 exferenceBot joined
03:17 lspitzner joined
03:17 systemfault joined
03:20 conal joined
03:21 MotherFlojo joined
03:22 conal joined
03:24 shayan_ joined
03:33 abhiroop joined
03:34 tom7942 joined
03:38 MotherFlojo joined
03:42 conal joined
03:46 hphuoc25 joined
03:50 takle joined
03:55 cschneid_ joined
03:55 tom7942 joined
03:56 madgoat joined
03:56 madgoat left
03:59 jamie_ joined
04:00 takle joined
04:07 takle joined
04:09 tom7942 joined
04:10 bruschkov joined
04:10 conal joined
04:13 abhiroop joined
04:16 Rodya_ joined
04:22 cschneid_ joined
04:25 conal_ joined
04:27 takle joined
04:44 abhiroop joined
04:48 malaclyps joined
04:49 takle joined
04:52 conal joined
04:53 abhiroop joined
05:00 takle joined
05:04 takle_ joined
05:11 bruschkov joined
05:11 takle joined
05:21 staffehn joined
05:22 takle joined
05:23 vicfred joined
05:26 takle joined
05:26 abhiroop joined
05:33 Rodya_ joined
05:41 takle joined
05:48 hphuoc25 joined
05:48 harfangk joined
05:48 jamie_ joined
05:49 ali_bush joined
05:49 ali_bush joined
05:56 takle joined
05:56 Deide joined
05:57 abhiroop joined
06:06 takle joined
06:13 bruschkov joined
06:14 howdoi joined
06:14 NANDgate joined
06:22 takle joined
06:23 cschneid_ joined
06:24 Cale joined
06:25 systemfault joined
06:30 takle joined
06:37 takle joined
06:37 abhiroop joined
06:38 Rodya_ joined
06:39 hphuoc25 joined
06:41 hphuoc25 joined
06:44 takle joined
06:47 <mounty> Can I ask again about the Reader Monad. I'm referring to Example 1 at the end of https://hackage.haskell.org/package/mtl-2.2.1/docs/Control-Monad-Reader.html
06:47 malaclyps joined
06:47 <mounty> Akii was kind enough to reply yesterday; are you here now Akii?
06:47 <mounty> I'm still having trouble understanding the line count <- asks (lookupVar "count")
06:49 <mounty> I can see the declaration of function asks on that page, but I still don't see how it goes from (lookupVar "count") to the int value count; specifically, it must apply (lookupVar "count") to bindings and I don't see how it does that.
06:49 <mounty> I see that runReader takes bindings as its second argument but it doesn't seem to be passed-in to calc_isCountCorrect anywhere.
06:50 <mounty> I understand higher-order (i.e., apparently incomplete) definitions like incr = (+) 1 but this isn't one of those, it seems to me.
06:52 <jle`> mounty: Reader's >>=/do notation doesn't actually apply (lookupVar "count") to anything directly
06:52 <jle`> mounty: it's all a way of building up a function in the end
06:53 justinfokes joined
06:54 <jle`> mounty: a 'Reader Bindings Bool' can be thought of as a 'Bindings -> Bool'
06:54 <jle`> so the entire do block is a way of "defining" a Bindings -> Bool
06:54 <jle`> of describing one
06:55 <jle`> in english, it'd be "well, my Bindings -> Bool is: (1) apply 'lookupVar "count"' to the input and call it count; (2) get the input and call it 'bindings', and then the resulting Bool is 'count == Map.size bindings'
06:55 thc202 joined
06:55 <jle`> calc_isCountCorrect doesn't actually compute a Bool
06:56 <jle`> it's a way of describing a function from Bindings -> Bool
06:56 <jle`> 'how you would make a Bool, if you had a Bindings available in your environment'
06:57 <mounty> jle` OK, thanks, I kind of see what you are saying; so the line (count == (Map.size bindings)) doesn't actually compare two integers ?
06:57 ThomasLocke joined
06:57 ThomasLocke joined
06:57 <mounty> I get the idea of the whole body being higher-order and passing-on a partial function rather than a value directly.
06:58 <mounty> But that line (count == (Map.size bindings)) looks like it compares two integers.
06:58 takle joined
06:58 <mounty> So in calc_isCountCorrect, count :: String -> Bool ?
06:59 <mounty> I don't get that.
06:59 <mounty> Sorry, count :: String -> Int
07:00 <mounty> Surely count :: Int ?
07:00 <jle`> mounty: count :: Int, here
07:00 <jle`> yes
07:00 <jle`> 'count == Map.size bindings' does compare two integers
07:01 <jle`> but they are the hypothetical integers you *would* get, from doing asks and ask
07:01 <mounty> OK, and "asks fn" results in a m a and in this case a is Int.
07:01 <jle`> yeah
07:01 <jle`> by line 3, you have a 'count :: Int'
07:01 <jle`> because you gave "instructions" on how to produce it
07:02 <jle`> sort of like in IO, you have s <- getLine
07:02 <jle`> then after that line, you can use 's :: String'
07:02 <jle`> you're basically using the result fo a previous computation in order to provide the next steps
07:03 <jle`> count <- asks (lookupVar "count") means 'get the "count" var of the environment, and name the result 'count'
07:03 <jle`> you can now use the result in the rest of the do lbock
07:04 <mounty> jle` Thanks; I have to step away from the KB for 1/2 or so. Thank you and let me come back to this.
07:04 <jle`> so, by the time you get to line 3, you have a (count :: Int) because you described how to get it from the environment (by using 'asks'), and you bound it to a name
07:04 <jle`> mounty: no problem! you can sort of compare it to IO, as well, if you're familiar with IO
07:04 <jle`> do s <- getLine; t <- getLine; return (s == t)
07:05 takle joined
07:06 abhiroop joined
07:10 patbecich joined
07:12 galderz joined
07:12 takle joined
07:15 bruschkov joined
07:15 hphuoc25 joined
07:19 cur8or joined
07:20 patbecich joined
07:24 unlaudable joined
07:28 takle joined
07:30 <mounty> jle` hello; I'm back. Thanks for your patience so far but I still don't 'get' it. Your IO example above is clear because in some sense getLine refers to a global Monad object and obtains the strings from it (OK, that's not to go in the next edition of LYAH but YSWIM),
07:30 aarvar joined
07:30 <mounty> But I wouldn't expect to write "s <- readLine" and get a string because readLine needs a filename argument so it knows from where to get its strings.
07:31 <jle`> mounty: a 'Reader Bindings a' is a Reader action that produces an 'a' from a Binding in the environment
07:31 <jle`> mounty: so `asks (lookupVar "count") :: Reader Bindings Int`
07:31 <jle`> `asks (lookupVar "count")` is a Reader action that produces an Int from a Binding in the environment
07:32 <jle`> `asks (lookupVar "count")` is a 'Reader Bindings Int', which does produce an Int when run
07:32 <mounty> This would make more sense if calc_isCountCorrect :: Bindings -> Bool and s/runReader/apply/
07:33 patbecich joined
07:33 <jle`> mounty: sure, that would be a way of directly building a Bindings -> Bool
07:33 <jle`> but here we're building a 'Reader Bindings Bool'
07:33 <jle`> which is an abstract data type
07:33 <jle`> but i think you get the picture
07:33 <* mounty> thinking hard
07:33 <jle`> `asks :: (r -> a) -> Reader r a`, here
07:33 hphuoc25 joined
07:34 <jle`> don't think about 'lookupVar "count"` as the function you're binding
07:34 <jle`> a 'Reader r a' *is* instructions to create an 'a', from an 'r' in the environment
07:35 <jle`> so, `asks (lookupVar "count") :: Reader Bindings Int`, is instructions to create an Int from a Bindings environment
07:35 <mounty> jle` OK, got that, then >>= gives access to the Int that it has produced.
07:35 <jle`> yeah
07:36 <jle`> so, you "run" that `Reader Bindings Int` to get the Int, and you can sequence it with >>=
07:36 <jle`> and you can bind the result (the Int) for later usage
07:36 <mounty> So it is the >>= that 'runs' (executes or evaluates) it.
07:37 <jle`> i'd say that >>= sequences it
07:37 <jle`> 'runReader' is what eventually runs it
07:37 hphuoc25 joined
07:37 <jle`> so you can use >>= with Reader to "sequence" successive asks
07:37 <jle`> sequence successive Reader actions
07:37 <mounty> Ah, OK. That makes sense because only runReader knows about the bindings value.
07:37 <jle`> and create a new Reader action
07:38 jamie_ joined
07:38 <jle`> yeah
07:38 <jle`> what'y oure doing with >>= is essentially describing a 'Binding -> Bool', by composing simpler 'Binding -> ...'s
07:38 <mounty> Thanks again jle` --- let me think over that one as I believe enlightenment is drawing close.
07:38 <jle`> and that's the advantage of the 'monadic' approach rather than just striaght up writing a Binding -> Bool
07:39 <jle`> you can sequence/compose simpler (Binding -> ...)'s, in order to build your final (Binding -> Bool)
07:39 bruschkov joined
07:40 bruschkov joined
07:41 <jle`> mounty: one way i like to think of Reader do blocks is "*if* i had a Binding, i could do this with it..."
07:42 <jle`> so in this case, it's like, "if i had a Binding, i could do `lookupVar "count"` with it and call it 'count'", etc.
07:42 mengu joined
07:43 greglearns joined
07:43 bruschkov joined
07:43 Rodya_ joined
07:44 <mounty> jle` yeah, I get that ... you're working at a higher level, with a function rather than a value but I'm still confused. If you write something like "($) ((+) 1) 3" then you know that ((+) 1) is a function and 3 is the value that ($) passes to it.
07:44 <jle`> mounty: yeah, you're building a function by sequencing simpler functions
07:44 <jle`> but, you do'nt have to think about it as a function
07:45 takle joined
07:45 <jle`> you can just think of 'Reader Binding Bool' as an abstract data type that produces a Bool from a Binding environment
07:45 <jle`> and think of 'asks' as a sort of abstract constructor/way to "define" a 'Reader'
07:45 <jle`> how to "make" a Reader primitive
07:46 <mounty> I do get that.
07:46 <jle`> for example, IO in Haskell is an abstract data type, and provides you with nice primitives like getLine and putStrLn
07:46 <jle`> Reader is an abstract data type that provides you with a nice primitive 'asks :: (r -> a) -> Reader r a'
07:46 <mounty> I get that as well.
07:47 <jle`> so, while you're building a Reader, you never "have" an 'r' directly; you just are assembling ways of how to produce that 'a' if you had an 'r'
07:47 <mounty> To adopt my example above, it's like writing "((+) 1 >>= sum" and sum==4 but how did I ever feed the 3 to it?
07:47 <jle`> ah yeah. you just need to stop thinking about 'Reader r a' as an 'a'
07:47 <jle`> a 'Reader r a' doesn't contain an 'a' in it
07:48 <mounty> Reader r a is a function r -> a
07:48 <jle`> there is no 'a' that lives inside a 'Reader r a'
07:48 <mounty> that's right .. it doesn't have the 'a' (bindings in the Example 1 to which I originally referred).
07:48 <jle`> not sure what ((+) 1 >>= sum is supposed to mean in this context
07:48 <mounty> It only has a function that will give you an a if you give it an r.
07:50 <jle`> yeah. well, in this case, Reader is an abstract data type, so you don't know if it 'contains' a function internally. that's an implementation detail
07:50 <mounty> Well I meant ((+) 1) >>= sum [dropped parenthesis] but I gave the example to explain my inability to see how/when/where 'bindings' is supplied to the Reader-wrapped function to yield count :: Int
07:51 <mounty> I re-wrote the body of calc_isCountCorrect as: calc_isCountCorrect = CMR.asks (lookupVar "count") >>= \count -> CMR.ask >>= \bindings -> return (count == Map.size bindings)
07:52 <mounty> so does 'runReader' effectively evaluate (CMR.asks (lookupVar "count") >>= \count -> CMR.ask >>= \bindings -> return (count == Map.size bindings) bindings
07:52 <jle`> yeah, i find that >>= with Reader makes things pretty opaque/unreadable
07:52 <jle`> mounty: runReader evalutes the 'Reader' that is described by whatever you wrote, yes
07:53 <jle`> remember like for IO, Maybe, Either e, etc., the "bound value" doesn't actually ever 'exist' until things are run/executed
07:53 louispan joined
07:54 <mounty> Right, so to return to your getLine example, I would write it as getLine >>= \s -> ....
07:54 <jle`> yeah
07:54 <jle`> the 's' doesn't actaully exist at the point where you are applying >>=
07:54 <mounty> and the point there is that \ introduces a lambda or function body.
07:54 abhiroop joined
07:54 <jle`> but >>= lets you say "what you would do next, if you had an 's'"
07:55 <mounty> exactly because s is a function parameter, not a value that exists at that point. The \ introduces a lambda or anonymous funcction.
07:55 <jle`> yeah. it's often called a continuation
07:55 <mounty> Oh THAT's what a continuation is .... I've seen that term in the literature and it's on my todo list to investigate it.
07:56 <mounty> But I have the possibility of a Haskell job coming up and thought Reader and Writer monads were a bigger shortcoming in my knowledge.
07:56 <jle`> yeah, 'bind' is sort of a manifestation of the continuation pattern that pops up in a lot of contexts in programming
07:56 <mounty> Better to get them sorted-out ahead of any interview.
07:56 <jle`> if you have a 'Reader r a', then you have a way to produce an 'a', neat
07:57 <jle`> but, maybe you could "do" something with that 'a', once you get it?
07:57 <jle`> you could maybe apply it to a (a -> Reader r b)
07:57 <jle`> and you use (>>=) :: Reader r a -> (a -> Reader r b) -> Reader r b
07:57 <jle`> and voila, now you have a "Reader r b'
07:57 <jle`> you've transformed a 'Reader r a' into a 'Reader r b' by giving a way to "continue" from that 'a' to end up with a 'b'
07:58 <jle`> same for '(>>=) :: IO a -> (a -> IO b) -> IO b' -- you have an 'IO a', but you can transform it into an 'IO b' by providing "what to do next, with that 'a' you get"
07:59 <mounty> Yes but with IO you can do it more neatly with fmap
07:59 <mounty> Reader isn't a functor of course.
07:59 <jle`> Reader is actually a Functor
07:59 <jle`> well, 'Reader r'
07:59 <mounty> Oh!
07:59 <mounty> Yeah, OK.
07:59 takle joined
08:00 <jle`> i guess you could call 'fmap' a manifestation of the continuation pattern too
08:00 <mounty> I suppose so.
08:00 <jle`> but yeah, when you use (>>=), you're transforming a 'Reader r a' into a 'Reader r b', by showing how to use the 'a' that is produced
08:01 <jle`> so here we use (>>=) to turn a Reader Bindings Int into a Reader Bindings Bool
08:01 <jle`> by showing what to do with the Int that is produced
08:07 takle joined
08:07 flemming joined
08:14 takle joined
08:15 kritzcreek joined
08:16 <mounty> Thanks jle`; I'm just playing around with the Example 1 code now. Thank you very much for your patience.
08:16 Kuros joined
08:17 bruschkov joined
08:18 jle` joined
08:20 slomo joined
08:21 xiongmao86 joined
08:22 takle joined
08:23 <xiongmao86> Hi everyone, what does (# row, col #) mean? Is it a matching pattern?
08:23 <geekosaur> it's an unboxed tuple
08:24 <xiongmao86> geekosaur: thanks.
08:24 <geekosaur> (this is an internal detail, it's a bit faster than a normal tuple and has some other special behaviors, most notably that the tuple itself *must* be defined --- although it is still possible for the things within it to be _|_)
08:31 galderz joined
08:32 <xiongmao86> geekosaur: Thanks, the relevant docs is hard to find. Especially with (#,#). Are there any way to find it in document without reading entire ghc user guide?
08:36 <geekosaur> I gave you the key phrase, and it's right in the table of contents. https://downloads.haskell.org/~ghc/latest/docs/html/users_guide/glasgow_exts.html#unboxed-tuples
08:36 <geekosaur> you likely want to read the whole section on unboxed types and primitive operations, which that is the final section of
08:36 <geekosaur> s/section of/part of/
08:37 hphuoc25 joined
08:38 takle joined
08:38 <xiongmao86> geekosaur: Oh, I can find it with your words, what I want to ask is if I didn't know the key phrase. If I had only "(# row, col #)" phrase in mind.
08:39 <geekosaur> then you ask in here, or maybe try symbolhound
08:39 <geekosaur> http://symbolhound.com/
08:39 <MarcelineVQ> another option is to scan the file you found them in and look at what extensions are at the top, but then you'd have to first guess that it's an extension
08:40 <MarcelineVQ> notation is hard to search for for sure
08:41 <xiongmao86> geekosaur: MarcelineVQ: Thank you very much.
08:43 Durz0 joined
08:44 flemming joined
08:45 Rodya_ joined
08:46 fbergmann joined
08:51 <Akii> I've a general question about exceptions. In this code, what happens if the async part throws an exception? http://lpaste.net/352753
08:51 <Akii> would I catch this in the `finally` part?
08:54 takle joined
08:56 david joined
08:56 <MarcelineVQ> is what where you `wait` for it?
08:56 <david> what is a good small project to learn haskell fundamentals?
08:57 <MarcelineVQ> *is that
08:57 <Akii> MarcelineVQ: not waiting for anything
08:57 <Akii> just let it run; maybe I should replace that by forkIO
08:58 <Guest43672> what is a good small project to learn haskell fundamentals?
08:58 <Akii> Guest43672: your own
08:58 <Guest43672> that's the idea
09:01 <Akii> MarcelineVQ: I'd let it run and then cancel in the exception handling, if that makes sense
09:01 <Akii> along with other cleanup stuff
09:02 <Akii> just wondering what's happening if an exception is thrown before
09:02 takle joined
09:04 harfangk joined
09:05 AndreasK joined
09:06 <MarcelineVQ> It's worth testing but I wouldn't expect that finally to trigger if your async fails. You'd be better off using bracket to start the async and play the role of the finally after it
09:07 takle joined
09:10 mattyw joined
09:14 grdryn joined
09:14 cschneid_ joined
09:15 takle joined
09:16 louispan joined
09:16 <Akii> MarcelineVQ: the exception is just catched inside the async, nothing bubbles up
09:16 <MarcelineVQ> I'm fuzzy on it but the asyncornous exception raised by async when it's done with its mask could possible be raised before the mask of your finally is in effect, which is why I would bracket, so that a mask for asynchronous exceptions is active for the whole job. when an asyncronous exception crops up comes down to how throwTo works and I'm a bit fuzzy on that
09:17 justinfokes joined
09:19 nacon joined
09:19 nacon joined
09:20 <MarcelineVQ> Akii: hmm I suppose so, if you use wait it'll rethrow a present exception though
09:22 <Akii> well I use async to start two web server processes, so they really need to handle any exceptions themselfes
09:22 <Akii> I've to investigate this more but atm this is ok
09:22 xiongmao86 left
09:22 <Akii> need to try this with fork as well
09:23 <Akii> okay, doesn't halt the program but prints it
09:23 gregman_ joined
09:23 ilja_kuklic joined
09:26 <MarcelineVQ> in plain english what is the job of the snippet you pasted? :>
09:27 jamie_ joined
09:28 <Akii> let stuff run until someone interrups the program
09:28 <Akii> (that someone being supervisord)
09:32 <MarcelineVQ> That doesn't really match up with the code that I read here. To me it reads "Run another process whose result we don't care about, then getLine, if getLine throws an exception do ..."
09:32 <MarcelineVQ> The "result we don't care about part" is my inferrece from you saying you're not using wait though, I guess that's not an explicit part of the snippet
09:32 <MarcelineVQ> Is that an accurate statement? If it's not could you word what it does in that way
09:34 <Akii> the result is unit
09:34 <Akii> so ye, don't care about it
09:34 <Akii> to me this is just a convenient way of stopping the process in the case of an async exception
09:37 Atrumx joined
09:38 takle joined
09:38 <Akii> alternatively I could waitCatch on the async of course
09:39 <Akii> now I press enter and the program terminates
09:39 fulcrum joined
09:41 fhoffmeyer joined
09:41 madjestic joined
09:44 greglearns joined
09:44 takle joined
09:49 Rodya_ joined
10:01 bradley joined
10:04 bruschkov joined
10:15 unlaudable joined
10:19 justinfokes joined
10:22 staffehn joined
10:22 aarvar joined
10:26 agates left
10:27 NoCreativity joined
10:40 mengu joined
10:43 moei joined
10:54 Rodya_ joined
10:55 mthek joined
10:59 bruschkov joined
11:16 jamie_ joined
11:19 justinfokes joined
11:22 ederign joined
11:28 greglearns joined
11:30 cschneid_ joined
11:34 merijn joined
11:35 bruschkov joined
11:40 patbecich joined
11:42 hphuoc25 joined
11:44 <* sudoreboot[m]> sent a long message: sudoreboot[m]_2017-02-20_11:44:24.txt - https://matrix.org/_matrix/media/v1/download/matrix.org/izCjVOqssDOUvoEwvexXIvVG
11:50 <sudoreboot[m]> I don't know if perhaps this type of question is more suited for #haskell-game, but I feel more like a beginner, so I don't want to disrupt more educated discussions.
11:50 patbecich joined
11:56 Miroboru joined
11:57 Rodya_ joined
12:02 <MarcelineVQ> game is pretty slow, I'd go ahead and ask this in #haskell because it's the most active channel so you're more likely to be seen
12:03 NoCreativity joined
12:07 <sudoreboot[m]> MarcelineVQ: Will do, thanks
12:26 deank joined
12:28 BernhardPosselt joined
12:29 <BernhardPosselt> hi: data Writer w a = Writer { runWriter :: (a, w) }
12:29 <BernhardPosselt> is that a shorthand syntax for instances?
12:30 <PiDelport> Deriving?
12:30 <MarcelineVQ> no it's called record notation, it's a way of defining a getter of sorts for your values
12:30 <PiDelport> Oh, sorry, I misread the syntax.
12:31 <BernhardPosselt> thanks
12:31 <PiDelport> BernhardPosselt: That's basically a shorthand for defining:
12:31 <PiDelport> data Writer w a = Writer (a, w)
12:31 <PiDelport> runWriter (Writer (a, w)) = (a, w)
12:31 <PiDelport> The runWriter is a field accessor function.
12:31 abhiroop joined
12:31 <PiDelport> (There's only one field in this case, though.)
12:32 <PiDelport> There's also a bit more to record syntax in pattern matching syntax, but that's the gist.
12:34 <abhiroop> Are there any courses or recommended books to understand PL Theory notations?
12:34 <BernhardPosselt> oh i see :D
12:34 <BernhardPosselt> thats nice
12:34 <abhiroop> I came across http://siek.blogspot.in/2012/07/crash-course-on-notation-in-programming.html
12:34 <BernhardPosselt> so runWriter is misleading
12:34 <BernhardPosselt> getResult?
12:34 <BernhardPosselt> or extractß
12:34 <BernhardPosselt>
12:36 <merijn> abhiroop: Not that I'm aware of. Which notation confuses you?
12:38 <abhiroop> merijn: I was trying to go through this paper: https://pdfs.semanticscholar.org/b49e/9c2d00acd25ada608170c3c3485880261980.pdf
12:38 <PiDelport> BernhardPosselt: Well, in this case, it also does what the running of the writer does, so it's a bit of a pun.
12:38 <abhiroop> I got really intimidated by all the symbols in page 5
12:38 <PiDelport> BernhardPosselt: So it's just named that way so you can use it as "runWriter" against Writer values.
12:39 <abhiroop> For example : Γ ⊢TY σ : κ Not sure what this means
12:39 <merijn> abhiroop: That's...not an easy paper ;)
12:39 <merijn> Γ (Gamma) is usually a variable representing "some" environment
12:39 <BernhardPosselt> abhiroop: i suppose you need to understand everything 100% before you read these kinds of things ;D
12:40 <merijn> abhiroop: X ⊢ Y means "we can conlude Y from X"
12:41 <merijn> abhiroop: The above line/below notation is "natural deduction" and you can read it "IF stuff above line THEN stuff below line"
12:41 Pupnik joined
12:42 <abhiroop> merijn: Yeah the last bit I knew :)
12:42 <merijn> abhiroop: Also, how much background do you have that you're tackling this paper?
12:43 <abhiroop> I am planning to work on Eta: https://github.com/typelead/eta
12:43 <abhiroop> So the founder of the project asked me to take a look at this paper
12:44 <abhiroop> I need to basically study and understand Core
12:44 <abhiroop> I am also trying to go through the Spineless Tagless G machine paper by SPJ
12:45 <abhiroop> That seems a little less daunting
12:45 <abhiroop> This paper seems impenetrable :(
12:45 <merijn> abhiroop: The STG one is pretty readable, this one...looks daunting to me :p
12:46 <merijn> abhiroop: Well, one problem is learning how to read academically: which involves lots of skimming and skipping everything you don't understand, and then rereading, rather than trying to understand everything in one go
12:46 <abhiroop> merijn: True that
12:46 <merijn> abhiroop: Also, if you're interested in type theory and want to go into this, I can (strongly) recommend getting a copy of Types and Programming Languages
12:47 <abhiroop> With Jeremy Sieks blog post I could go through very basic type theory papers
12:47 <merijn> abhiroop: Which is *the* intro to type theory book, which basically starts at "untyped lambda calculus" and works up from there to "every complicated stuff"
12:47 <merijn> @where tapl
12:47 <lambdabot> http://www.cis.upenn.edu/~bcpierce/tapl/
12:47 <abhiroop> But most people have recommended me to pick up TAPL
12:47 <merijn> abhiroop: Note that TaPL was intended as an (under)grad textbook, so way more accessible than papers :)
12:47 <abhiroop> to understand more advanced haskell papers
12:50 <merijn> abhiroop: That'll almost certainly be the least confusing route, yes
12:50 <abhiroop> Thanks merijn
12:51 <merijn> abhiroop: TaPL should get you from "huh?!" to "I feel like I could implement a Haskell (well, without extensions...) type checker"
12:51 patbecich joined
12:52 wei2912 joined
12:57 Miroboru joined
13:02 Rodya_ joined
13:05 jamie_ joined
13:21 justinfokes joined
13:22 Gloomy joined
13:42 hphuoc25 joined
13:50 harfangk joined
13:51 kadoban joined
13:52 Gurkenglas joined
13:54 superlinux joined
13:54 <superlinux> hello
13:55 <BernhardPosselt> hi
13:55 <superlinux> I just want to say that I have translation into Arabic using youtube videos section 11.1.
13:56 <superlinux> translating the book learn you haskell
13:56 <BernhardPosselt> id contact the people via mail then
13:56 <qu1j0t3> superlinux: hey, long time no see
13:56 <superlinux> hey
13:56 <superlinux> yeah .. busy as they say
13:57 bamurphymac joined
13:57 <superlinux> I skipped chapter 10
14:00 <superlinux> translating the functors redux section was really hard
14:01 fhoffmeyer joined
14:01 hphuoc25 joined
14:03 <superlinux> Arab immigrants to Germany they are telling me that they are taught Haskell with the german language before learning C++ or any imperative language. I know german language has nothing to here. but it's just how they are learning
14:05 <qu1j0t3> well that's something
14:05 <qu1j0t3> i wonder if that is widespread though, or just some schools?
14:05 Rodya_ joined
14:06 <superlinux> those students are finding it very hard.. so my videos are soothing it up on them
14:08 Gloomy joined
14:08 <superlinux> qu1j0t3, I don't know. I have to ask
14:09 <superlinux> I hop I can teach haskell in some uni here in beirut
14:09 <superlinux> *I hope
14:22 justinfokes joined
14:23 greglearns joined
14:34 pbrant joined
14:35 netheranthem joined
14:36 galderz joined
14:46 oconnorct1 joined
14:49 hphuoc25 joined
14:54 patbecich joined
14:54 vicfred joined
14:54 jamie_ joined
14:56 chlong joined
15:04 galderz joined
15:04 mjs2600 joined
15:07 Rodya_ joined
15:14 Big_G joined
15:27 cschneid_ joined
15:29 Gloomy joined
15:36 fhoffmeyer joined
15:48 deeplearner joined
15:49 LiaoTao joined
15:53 ederign joined
15:54 conal joined
15:55 patbecich joined
15:56 greglearns joined
15:59 begriffs joined
16:05 galderz joined
16:09 contiver joined
16:09 Glooomy joined
16:10 Rodya_ joined
16:13 Glooomy joined
16:13 justinfokes joined
16:31 superlinux joined
16:31 superlinux joined
16:32 carlomagno joined
16:35 jathan joined
16:37 fhoffmeyer joined
16:40 gpo joined
16:44 jamie___ joined
16:55 hphuoc25 joined
16:58 superlinux joined
16:58 superlinux joined
17:07 hxegon joined
17:07 conal joined
17:09 oracle_ joined
17:09 Cthalupa joined
17:09 prophile joined
17:11 kini joined
17:11 oracle__ joined
17:14 jackhill joined
17:15 Rodya_ joined
17:18 Rodya_ joined
17:24 simendsjo joined
17:33 mthek joined
17:36 contiver joined
17:36 fhoffmeyer joined
17:39 MotherFlojo joined
17:39 contiver_ joined
17:39 initiumdoeslinux joined
17:44 polsab joined
17:56 patbecich joined
18:00 tom7942 joined
18:01 conal joined
18:03 Lokathor joined
18:04 <Jannoo> good afternoon
18:05 <Jannoo> im having a lot of trouble with the class heirchies for numbers
18:05 <Jannoo> for example, giveen this type signature: arith :: Num b => (a -> b) -> Integer -> a -> b
18:06 <Jannoo> why doesn't this work: arith f i x = (f x) + i
18:06 pilne joined
18:06 <Jannoo> (f x) should give us a Num
18:06 <Jannoo> and i is an Integer
18:06 <Jannoo> shouldn't we be able to add them together
18:06 <glguy> You need fromInteger
18:06 <glguy> f x :: b
18:06 delexi joined
18:07 <monochrom> No, f x doesn't give a Num. f x gives b, b belongs to Num, but you still don't know what b is.
18:07 <monochrom> (+) insists that both operands must be known to have the same type. But you don't know that Integer equals b.
18:08 <monochrom> fromInteger is there to convert Integer i to type b.
18:08 persona_ingrata joined
18:09 <Jannoo> why doesn't type inference work here. shouldnt the ghci be able to infer which concrete type b needs to become to allow the addition operation with i
18:09 <glguy> The type 'b' will be instantiated by the user of 'arith'
18:09 <glguy> There's nothing more to learn about it when checking the implementation of arith
18:10 <glguy> By writing that 'arith' has the type you did, you're asserting that we can't make any assumptions about what that type 'b' was
18:10 <glguy> other than that it has a Num instance
18:12 <Jannoo> i think i get it. thanks glguy and monochrom
18:12 <Jannoo> i'm sure i'll be back with more :)
18:13 <hexagoxel> :t \f i x -> (f x) + i
18:13 <lambdabot> Num a => (t -> a) -> a -> t -> a
18:14 <Jannoo> oooooooh
18:14 <Jannoo> got it, thanks guys!
18:16 Deide joined
18:17 <Jannoo> but wait, why are we trying to convert i into a more generic type instead of making (f x) more concrete, namely and Integer?
18:17 <Jannoo> namely an Integer*
18:18 <Jannoo> oh, because the type signautre says that we need to return a b
18:18 patbecich joined
18:18 sherub joined
18:19 <hexagoxel> for the given expression (without fromInteger) you could only make the type more specific than what was inferred above.
18:19 contiver__ joined
18:19 <hexagoxel> so if you want to specialize to a=Integer, you end up with (t -> Integer) -> Integer -> t -> Integer
18:20 <Jannoo> brilliant, thanks hexagoxel
18:20 <hexagoxel> if you want input/output type to differ, you need to convert somehow, somewhere.
18:22 merijn joined
18:22 <Jannoo> side question: so you can add to Nums but not a Num and an Integer?
18:22 <Jannoo> (where Num is a type class)
18:22 myrkraverk_ joined
18:22 <Jannoo> i think i got it
18:22 <hexagoxel> :t (+)
18:22 <lambdabot> Num a => a -> a -> a
18:23 eacameron joined
18:23 <hexagoxel> note that is not something like (Num a, Num b) => a -> b -> a/b
18:24 <Jannoo> because there is no guarantee that the specific instance of Num would have a defined result for addition to an Integer, right?
18:24 harfangk joined
18:26 <glguy> Jannoo: You *can't* add "two Nums"
18:26 <hexagoxel> are you asking why Num is designed this way? because otherwise, what glguy says.
18:26 <glguy> You can add two values of the exact same type as long as that one type has an instance of Num
18:27 chlong joined
18:27 tom7942 left
18:28 <Jannoo> oh man, i swear i think i got it now
18:28 Glooomy joined
18:29 <hexagoxel> and the fact that i used "a/b" in the hypothetical (+) type is already a hint that a different design would be .. strange/less beautiful.
18:29 <Jannoo> so in summation for: arith :: Num b => (a -> b) -> Integer -> a -> b
18:30 <Jannoo> arith f i x = (f x) + (fromInteger i)
18:30 lspitzner joined
18:31 <Jannoo> (fromInteger i) allows ghci to turn that into a specific type of typeclass Num where (f x) would be defined, based on the type of b which the user provides?
18:31 hoffmeyer joined
18:31 cale2 joined
18:32 <hexagoxel> :t fromInteger
18:32 <lambdabot> Num a => Integer -> a
18:32 <hexagoxel> :t \a b -> a + b
18:32 <lambdabot> Num a => a -> a -> a
18:32 <hexagoxel> :t \a b -> a + fromInteger b
18:32 <lambdabot> Num a => a -> Integer -> a
18:33 jamie___ joined
18:34 <Jannoo> thanks, let me ponder this for a while
18:34 <Jannoo> sorry, i know this must be very basic. thanks for bearing with me
18:35 <hexagoxel> communicating via type signatures feels cheap, but i am unsure how else to explain it.
18:36 <Jannoo> i understand. i think i might just be getting hung up on the details. i prob just need to accept that not everything has been revealed to me yet and just keep going. hold on to what i think i understand and be congnizent of what i dont and just keep reading.
18:36 <glguy> Jannoo: There's not much else to be revealed. In loose terms your statement about fromIntegral is OK
18:37 fhoffmeyer joined
18:37 <glguy> fromInteger :: Num a => Integer -> a; when you used it in your definition of arith you instantiated the type 'a' in the type of fromInteger to be 'b' from your type signature (automatically via type inference)
18:38 <hexagoxel> the rest is training of your type inference intuition to not mess up who gets to choose the specific types :)
18:39 <Jannoo> thanks guy. lunch and then back to reading :)
18:39 <Jannoo> guys8*
18:39 <Jannoo> guys***
18:44 <PiDelport> Jannoo: To give you another attempt at an explanation, (+) :: Num a => a -> a -> a means you may have a function (+) :: Integer -> Integer -> Integer, and another function (+) :: Double -> Double -> Double
18:44 mjs2600 joined
18:44 <PiDelport> But it doesn't give you any function (+) :: Integer -> Double -> Double
18:44 <PiDelport> Or any other mix.
18:44 <PiDelport> Each instance's (+) is just defined for those specific types.
18:45 <PiDelport> IOW, you can add apples and apples, and pears and pears, but not apples and pears.
18:48 bruschkov joined
18:48 <contiver__> what are the different stack resolvers? is it like a set of packages that all work together?
18:49 madjestic joined
18:51 <nitrix> contiver__: Correct.
18:52 <nitrix> contiver__: Currently, they're a snapshot of a subset of hackage. I'm saying that because I'm not aware of packages that are on stackage and not on hackage.
18:52 mjs2600 joined
18:53 <nitrix> contiver__: And I didn't say the "all work together" part because there are nightly resolvers that don't necessarily quite work together.
18:53 <nitrix> contiver__: The LTS ones are very stable and meant for Long Term Support though.
18:54 bruschkov joined
18:56 hphuoc25 joined
18:57 <contiver__> nitrix: which ones should I aim to support? Because I just tried the travis CI config from the stack website which builds against different versions and lts(es)
18:58 <contiver__> and it is working with lts 6, 7, and nightly
18:58 <contiver__> but failing with older ones.
18:58 <contiver__> mainly because of bounds.
18:59 fhoffmeyer joined
18:59 <nitrix> They're tied to a GHC version, so whichever GHC you want to support.
18:59 <nitrix> Personally, GHC 7.10 and GHC 8 are the most crucial to me. Below that, I think I'd just laugh at the user.
19:00 wildlander joined
19:01 contiver_ joined
19:03 bruschkov joined
19:07 contiver__ joined
19:10 Apocalisp joined
19:15 bruschkov joined
19:16 <Jannoo> PiDelport: Thank you. That makes perfect sense :)
19:23 greglearns joined
19:26 ilja_kuklic joined
19:31 asivitz joined
19:31 NoCreativity_ joined
19:33 conal joined
19:34 mjs2600 joined
19:38 emmanuel_erc joined
19:47 Gurkenglas_ joined
19:49 dansvidania joined
19:53 contiver_ joined
19:55 <dansvidania> Hello, I am trying the difference list exercise at the end of chapter 28
19:57 <dansvidania> I seem to fail to understand what is going on due to the fact that my implementation of the DList construction still takes the same time as with Lists although after trying for a few hours I had given up and read the tutorial in the followup resources
19:59 <dansvidania> http://lpaste.net/352788
20:01 albertus1 joined
20:02 takle joined
20:05 <ski> dansvidania : try adding the singleton at the end of the list instead
20:05 <ski> dansvidania : `append = mappend'
20:09 <dansvidania> Hello Ski, thank you for your answer
20:10 <dansvidania> do you mean changing the implementation of singleton = (++x) ?
20:10 <dansvidania> or switching them in the benchmark?
20:17 takle joined
20:20 <ski> dansvidania : not changing `singleton', i mean changing `schlemiel' and `constructDList'
20:21 greglearns joined
20:22 jamie___ joined
20:25 handlex joined
20:27 mjs2600 joined
20:28 MotherFl1 joined
20:28 <dansvidania> ski: that code was part of the exercise text
20:30 contiver__ joined
20:30 <dansvidania> appending the singleton does make constructDList slightly faster
20:31 <lpaste_> dansvidania pasted “results” at http://lpaste.net/352790
20:35 merijn joined
20:35 k4rtik joined
20:35 merijn joined
20:37 jomg joined
20:37 <Akii> anyone got an idea how to make this work? xD http://lpaste.net/352791
20:38 <Akii> or why it doesn't
20:40 <ski> dansvidania : if you repeatedly add to the start with `++' (or `:'), there should be no important difference with the DL version. if you add to the end, otoh ..
20:40 <ski> (unless the implementation manages to optimize the inefficient version ..)
20:41 <ski> Akii : wrong type signature
20:42 <Akii> :o
20:42 <ski> Akii : `mkAggregate' should not be polymorphic in `m' (nor have a `MonadError err m' constraint), since that means that the caller of `mkAggregate' should pick `m' (such that `MonadError err m' is satisfied)
20:43 <ski> Akii : assuming `Aggregate' is correct, `mkAggregate' wants to get two *polymorphic* functions as arguments, polymorphic in `m' (and with the constraint in each case)
20:43 <dansvidania> ski: Yeah I was unsure why snoc is not used in the benchmark
20:43 <ski> that way, the caller of `mkAggregate' will not pick `m', but rather be prepared for any `m' (so the *caller* (or the callbacks in the caller), not `mkAggregate', will be polymorphic in `m')
20:44 <ski> in general, this means that `mkAggregate' itself (the callee) will pick `m' (making sure `MonadError err m' holds), possibly using the polymorphic callbacks multiple times, with difference choices of `m'
20:45 <ski> in this particular case, however, `mkAggregate' will delegate actually picking `m' to whoever uses the result of type `Aggregate err ev a' that it returns
20:45 <Akii> I just thought I'd be nice to have this convenience function
20:45 oconnorct1 joined
20:45 <ski> you could define it, but the correct type signature would be
20:46 <ski> mkAggregate :: (forall m. MonadError err m => ev -> m a) -> (forall m. MonadError err m => a -> ev -> m a) -> Aggregate err ev a
20:46 <Akii> well that makes sense
20:46 <ski> note how the `forall' in the *argument* types means that those *arguments* are now required to be polymorphic
20:46 <ski> (and GHC can't infer such types, so you can't just ask GHCi what the type should be. you have to know, more or less, what to write ..)
20:47 <ski> you also need the extension `Rank2Types', in order to express this type signature
20:47 <ski> Akii : ok ?
20:48 <Akii> yup
20:48 <Akii> makes sense
20:48 <ski> (to declare `Aggregate', you need `PolymorphicComponents', but that's implied by `Rank2Types', so ..)
20:48 <Akii> (I'm probably not getting the full extent to this implication, but this works for my use-case)
20:48 <ski> *nod*
20:49 <ski> as long as you understand the issue, as being about needing to require the arguments to be polymorphic
20:49 <Akii> I basically stated this to be polymorphic in the data type itself
20:49 <ski> that can be useful in some other cases, for expressiveness, or for information hiding (not leaking implementation details through the type signature)
20:49 <ski> yes
20:49 <Akii> any two MonadError instances
20:50 <Akii> especially separate instances
20:50 <Akii> for each function
20:50 <ski> with your written type signature, the caller would pick some specific `m', so `mkAggregate' would get called with two callbacks that (as far as it knew, at least) *only* worked for that `m'
20:50 <Akii> (also, init shadows some existing binding, as always xD)
20:50 contiver__ joined
20:51 <ski> > init "good"
20:51 <lambdabot> "goo"
20:53 <ski> dansvidania : "appending the singleton" would be strange here, since then you'd always be repeatedly adding to the end, which was what DL was invented to avoid
20:53 <Akii> thanks ski
20:53 <Akii> as always
20:54 <Akii> @karma+ ski
20:54 <lambdabot> ski's karma raised to 50.
20:55 <dansvidania> let's see
20:55 Dextepot joined
20:56 Nik05 joined
20:56 <dansvidania> If I understood correctly DList uses the lazy applications of functions to convert a series of what would be left associative concatenations in a single series of cons operations
20:59 <ski> it would work similarly in an eager language as well
21:00 <ski> note how the implementation of the DL operations doesn't use `++' (except `empty', but that's a trivial use, which could easily be replaced with `id')
21:00 mengu joined
21:01 <ski> (well, also excluding `fromList' .. which you didn't write, though)
21:01 <ski> the point is that by this trick, we no longer get any left-associated applications of `++', like `(((as ++ bs) ++ cs) ++ ds) ++ es'
21:02 <ski> the problem there is that we traverse `as' in order to perform the first `++'. then we traverse (the copy of) `as' *again*, and also `bs', for the second `++'
21:02 <dansvidania> yes, I got this far
21:02 <ski> for each new `++' we need to traverse all the previous lists anew (or rather their copies)
21:02 <dansvidania> perfect, this is luckily clear to me
21:03 <ski> with DL, we instead get something like (((fromList as . fromList bs) . fromList cs) . fromList ds) . fromList es'
21:03 <ski> where `fromList xs = DL (xs ++)', so this is a use of `++'
21:03 contiver_ joined
21:03 <ski> but left-associating `.' like above is no problem
21:04 <ski> that translates into `\fs -> as ++ (bs ++ (cs ++ (ds ++ (es ++ fs))))'
21:04 <ski> so, we've magically changed the left-associations of `++' into right-associations
21:04 takle joined
21:04 <dansvidania> I understand
21:05 <dansvidania> but how is that used in the exercise? It seems to me that the original benchmark is right associative in both the List and the DList implementation
21:05 <ski> this is btw related to "continuation-passing style", and the same problem, with the same solution, crops up when making "tree monads", where left-associated uses of `>>=' behave similarly bad as `++' above
21:05 <ski> from what i can understand, the exercise is just plain wrong
21:06 <dansvidania> oh
21:06 <ski> (or perhaps you've misunderstood something in the exercise. i dunno, i haven't seen it)'
21:06 <merijn> ski: fwiw, if next time you're too lazy to explain that, there's an excellent link for this ;)
21:06 <dansvidania> well, I am glad I've spent the last 4 or 5 hours trying to figure it out XD
21:06 <ski> if it's from Haskellbook, you could try mailing the authors and asking
21:06 <merijn> http://h2.jaguarpaw.co.uk/posts/demystifying-dlist/
21:06 <ski> merijn : too lazy to explain diff-lists, what's that ? ;)
21:07 <dansvidania> thanks ski
21:07 <dansvidania> @karma+ ski
21:07 <lambdabot> ski's karma raised to 51.
21:07 <merijn> What was the original question?
21:07 <MarcelineVQ> it's come up before, I think the bench is put together wrong or at least not as well as it can be
21:08 <merijn> As in, assignment :)
21:08 <dansvidania> merijin: one moment please, I will paste it
21:09 <MarcelineVQ> dansvidania: side-note, you don't need monoid in this exercise, the bench uses 'append' not 'mappend' not that it's wrong to use it or impacts the result
21:10 <dansvidania> yeah, I was trying it out
21:10 <lpaste_> dansvidania pasted “Difference list exercise Chapter 28” at http://lpaste.net/352793
21:11 <ski> dansvidania : btw, the `Show' type class uses diff-lists
21:11 <dansvidania> interesting :D
21:12 <ski> one could also note that there's a similar, but not quite the same, notion of "difference list", in logic programming (like Prolog,Oz,LambdaProlog,...)
21:12 <ski> @src Show
21:12 <lambdabot> class Show a where
21:12 <lambdabot> showsPrec :: Int -> a -> ShowS
21:12 <lambdabot> show :: a -> String
21:12 <lambdabot> showList :: [a] -> ShowS
21:12 <ski> @src ShowS
21:12 <lambdabot> type ShowS = String -> String
21:12 <ski> that's the diff-list
21:12 <ski> @type showChar
21:12 <lambdabot> Char -> ShowS
21:12 <ski> @type showString
21:12 <lambdabot> String -> ShowS
21:12 <ski> @type showParen
21:12 <lambdabot> Bool -> ShowS -> ShowS
21:12 <MarcelineVQ> a simple parens change can make a big difference here btw, go n xs = go (n-1) [n] ++ xs vs go n xs = go (n-1) ([n] ++ xs)
21:13 <merijn> I'm not sure "twice as fast" is indeed what you should expect, but the exercise seems reasonable enough?
21:13 <dansvidania> well that runs in the same amount of time as they are both cons-ing one element per recursion
21:14 <dansvidania> at least that's what i've got so far
21:14 <ski> as you may have guesses, you want to use `toList' as little as possible, with DLs
21:14 <merijn> I would expect the DList one to be faster
21:15 <merijn> Rather a lot, unless you've implemented it wrong ;)
21:15 <dansvidania> which is very possible indeed
21:15 <dansvidania> http://lpaste.net/352788
21:16 <dansvidania> merijn: would you mind taking a look? I am desperate for pointers, at this point
21:16 <dansvidania> (no pun intended)
21:17 <merijn> empty looks suspicious, but not to the extent that they should be equally fast (or slow...)
21:18 <dansvidania> well, they do on my machine...
21:19 <merijn> Are you compiling with -O2?
21:19 madjestic joined
21:19 <merijn> oh!
21:19 <merijn> Shouldn't do tests use nf, rather than whnf?
21:20 <dansvidania> oh, wait a minute, wouldn't (go (n-1) [n]) ++ xs make much more sense?
21:21 <dansvidania> MarcelineVQ: now I understand what you meant
21:21 <MarcelineVQ> first, rather, I think the test case is too small, try 1234567 before modifying things
21:23 greglearns joined
21:24 <dansvidania> still the same time with 1234567
21:24 MotherFlojo joined
21:25 <dansvidania> and even eliminating the parenthesis the difference is marginal
21:25 <merijn> whnf only constructs the head of the list, which seems an odd benchmark
21:25 <merijn> Hence why I think it should be nf
21:25 <dansvidania> will try
21:26 <MarcelineVQ> I think nf shouldn't matter much, you need to resolve the nesting to get the head
21:30 oconnorct1 joined
21:30 <dansvidania> oh wow nf is taking quite a while :D
21:31 <MarcelineVQ> hmm, that parens change should have made an obvious difference, how are you running this test?
21:32 <dansvidania> in nf the parens change makes a whole lot of difference
21:33 <dansvidania> anyway I am loading the script in ghci, is it the wrong way?
21:33 <MarcelineVQ> yes :>
21:33 <dansvidania> aha
21:33 <MarcelineVQ> in most cases benchmarking should be done with optimizations on which ghci does not do
21:34 <merijn> oh...
21:34 <merijn> That explains so much...
21:34 <dansvidania> yeah..
21:34 <dansvidania> well... I guess I deserved banging my head against my desk for a couple of hours
21:35 <MarcelineVQ> well I still think the bench's aren't setup quite the way they should be, but your numbers should be more in line if you run it as written in the book but optimized
21:35 seagreen joined
21:40 ljc joined
21:40 <dansvidania> trying right now
21:53 hiratara joined
21:54 aarvar joined
21:54 jmiven joined
21:56 Gurkenglas joined
21:56 Durbley joined
22:05 <Hijiri> /buffer 43
22:06 <dansvidania> well, i must be doing something wrong still
22:06 <dansvidania> with the optimizations both implementantions get much faster, but I still don't see much of a difference
22:06 <dansvidania> with or without the parens
22:07 <dansvidania> 13 ms vs 10 ms on average
22:07 <dansvidania> lol even with 1234567 they go up to 148 vs 141
22:11 jamie___ joined
22:15 louispan joined
22:19 fhoffmeyer joined
22:25 takle joined
22:25 MotherFlojo joined
22:29 Rodya_ joined
22:29 mthek joined
22:31 louispan joined
22:31 hiratara joined
22:32 MotherFlojo joined
22:36 jmla joined
22:37 <MarcelineVQ> dansvidania: dunno at this point
22:38 <dansvidania> is it even possible that ghc is optimizing the one with the standard list as well?
22:40 <dansvidania> the difference is very clear in using nf
22:41 <dansvidania> I don't get why though
22:42 <MarcelineVQ> I wonder what the difference is, running your exact paste from earlier with -O2 gives me 11 vs 5 ms
22:43 <merijn> dansvidania: whnf only evaluates until the first constructors, nf evaluates the entire list
22:43 <merijn> dansvidania: Which has a more dramatic impact, obviously
22:44 <dansvidania> yeah but shouldn't whnf go through the entire nesting before it can pull the head of the list?
22:44 louispan joined
22:45 <dansvidania> also using nf with the given exercise runs for waaaay too long
22:45 <dansvidania> I had to scale it down one digit to make it produce results
22:45 <dansvidania> (in a reasonable amount of time)
22:46 MotherFlojo joined
22:49 <lpaste_> dansvidania pasted “results” at http://lpaste.net/352795
22:50 <dansvidania> well, I'm moving on before this drives me mad
22:56 Rodya_ joined
22:58 conal joined
22:59 hphuoc25 joined
23:15 MotherFlojo joined
23:20 fhoffmeyer joined
23:21 cschneid_ joined
23:25 jmla joined
23:26 malaclyps joined
23:27 polsab_ joined
23:28 <jmla> I'm having a hard time with the QuickCheck part of the 15.12 exercise "Maybe another monoid" in haskellbook. It seems like I have to set up arbitrary instances of both First' a and Optional a, right?
23:29 <jmla> and I'm getting my First' a instance set up but I can't get an optionalGenerator working
23:30 <MarcelineVQ> you do. what is optionalGenerator?
23:32 <jmla> Ahhh ok, I found the Maybe instance explained in chapter 14
23:32 <jmla> with fequency [(1, return Nothing), (3, liftM Just arbitrary)]
23:36 begriffs joined
23:37 contiver__ joined
23:51 polsab joined
23:52 mac10688 joined
23:53 Gloomy joined
23:54 Gloomy joined
23:54 begriffs joined
23:54 Gloomy joined
23:55 Gloomy joined
23:56 begriffs joined
23:56 Gloomy joined
23:57 Gloomy joined