Available formats: content-negotiated html turtle (see SIOC for the vocabulary)
Back to channel and daily index: content-negotiated html turtle
These logs are provided as an experiment in indexing discussions using IRCHub.py, Irc2RDF.hs, and SIOC.
| 00:14:37 | <hpaste> | SamB annotated "difficult Coq Lemma" with "Where I get stuck with the Set version..." at http://hpaste.org/8013#a4 |
| 00:14:40 | <travisbrady_> | :t fromListWith |
| 00:14:42 | <lambdabot> | Not in scope: `fromListWith' |
| 00:14:50 | <travisbrady_> | :t Data.Map.fromListWith |
| 00:14:52 | <lambdabot> | forall a k. (Ord k) => (a -> a -> a) -> [(k, a)] -> M.Map k a |
| 00:41:03 | <Peaker> | raytrace: Error in array index -- any way to get a traceback/line num/etc? |
| 00:41:36 | <dmwit> | Use assert? |
| 00:43:39 | <dbueno> | Peaker: http://www.haskell.org/ghc/docs/latest/html/users_guide/ghci-debugger.html#ghci-debugger-exceptions |
| 00:43:40 | <lambdabot> | Title: 3.5. The GHCi Debugger, http://tinyurl.com/2orwlb |
| 00:44:19 | <Eiler> | dons: that dynamic loaded plugins at summer of code, is that something similiar to hs-plugins? |
| 00:44:19 | <dbueno> | Peaker: The section from the manual is entitled "Debugging exceptions" but really all the info about the GHCi debugger is useful. |
| 00:44:31 | <NRee1> | hey is there a way to limit the memory ghci can use? |
| 00:44:39 | <Peaker> | dbueno, thanks |
| 00:44:41 | <NRee1> | I find it painful for it to page out firefox etc |
| 00:47:47 | <TomMD> | Sure is - just use GHC in a Xen VM and limit that VM to X megs. |
| 00:47:59 | <EvilTerran> | ha |
| 00:48:18 | <bd_> | TomMD: or use +RTS heap size limits |
| 00:48:25 | <TomMD> | I like my way. |
| 00:48:27 | <NRee1> | hehe ya good way to keep memory usage down ^^ |
| 00:48:33 | <bd_> | +RTS -Mmaxsize |
| 00:49:55 | <NRee1> | thanks bd_ thats what I was looking for |
| 00:50:05 | <NRee1> | but I think TomMD's was more clever ;) |
| 00:50:26 | <TomMD> | :) |
| 01:13:38 | <hpaste> | morrow pasted "sqlite3-amalgamation.sh" at http://hpaste.org/8015 |
| 01:16:45 | <hpaste> | morrow annotated "sqlite3-amalgamation.sh" with "better" at http://hpaste.org/8015#a1 |
| 01:28:59 | <TomMD> | Arrr, I miss my community.h.o account! |
| 01:29:09 | <hpaste> | (anonymous) pasted "(no title)" at http://hpaste.org/8016 |
| 01:29:18 | <NRee1> | why does that stack overflow? |
| 01:30:49 | <ddarius> | :t Text.ParserCombinators.Parsec.chainl |
| 01:30:52 | <lambdabot> | forall tok st a. Text.ParserCombinators.Parsec.Prim.GenParser tok st a -> Text.ParserCombinators.Parsec.Prim.GenParser tok st (a -> a -> a) -> a -> Text.ParserCombinators.Parsec.Prim.GenParser tok |
| 01:30:52 | <lambdabot> | st a |
| 01:30:53 | <ddarius> | :t Text.ParserCombinators.Parsec.chainr |
| 01:30:55 | <lambdabot> | forall tok st a. Text.ParserCombinators.Parsec.Prim.GenParser tok st a -> Text.ParserCombinators.Parsec.Prim.GenParser tok st (a -> a -> a) -> a -> Text.ParserCombinators.Parsec.Prim.GenParser tok |
| 01:30:55 | <lambdabot> | st a |
| 01:32:44 | <mar77a> | is there anyway to pattern match an array |
| 01:32:52 | <mar77a> | like you do f (x:xs) for lists, but for an array? |
| 01:33:17 | <mauke> | no |
| 01:33:41 | <ddarius> | NRee1: Try compiling with -O2 |
| 01:33:53 | <ddarius> | :t Text.ParserCombinators.Parsec.chainr1 |
| 01:33:55 | <lambdabot> | forall tok st a. Text.ParserCombinators.Parsec.Prim.GenParser tok st a -> Text.ParserCombinators.Parsec.Prim.GenParser tok st (a -> a -> a) -> Text.ParserCombinators.Parsec.Prim.GenParser tok st |
| 01:33:55 | <lambdabot> | a |
| 01:37:01 | <ddarius> | :t \a b -> ord <$> a <*> b |
| 01:37:03 | <lambdabot> | Couldn't match expected type `a -> b' against inferred type `Int' |
| 01:37:03 | <lambdabot> | Probable cause: `ord' is applied to too many arguments |
| 01:37:03 | <lambdabot> | In the first argument of `(<$>)', namely `ord' |
| 01:37:13 | <ddarius> | :t \a b -> (+) <$> a <*> b |
| 01:37:15 | <lambdabot> | forall a (f :: * -> *). (Applicative f, Num a) => f a -> f a -> f a |
| 01:48:12 | <NRee1> | ddarius: compiling worked like a charm |
| 01:48:23 | <NRee1> | so does compiling increase the stack space? |
| 01:48:46 | <EvilTerran> | it means a lot of optimisations get done that wouldn't be otherwise |
| 01:49:13 | <SamB> | it makes better use of stack space |
| 01:49:32 | <SamB> | I'm not sure if it can make better asymptotic use of stack space or not... |
| 01:50:17 | <ddarius> | NRee1: I suspect the problem is that the definition of maximum in GHC relies on strictness analysis. |
| 01:51:31 | <NRee1> | ya from my little analysis, i noticed maximum was the "stack overflower" in the sense that if it was removed and I just straight printed the list, it wouldnt crash |
| 01:55:52 | <scriptdevil> | [Not homework but prereading for it] I am assigned a project to develop an almost Version 0 compiler from one language to another. As pre-reading, I have now come to understand the haskell syntax fluently. But is there any book specifically aimed at writing a parser so that I make efficient use of the libraries |
| 01:55:57 | <scriptdevil> | ? |
| 01:57:14 | <lament> | there's... the parsec homepage :) |
| 01:57:32 | <dolio> | Parsec is probably the most used library for parsing. |
| 01:58:00 | <jeffz> | I also recommend the parsec homepage... |
| 01:58:02 | <dolio> | There are papers/manuals about it, although they're probably somewhat out of date (not fundamentally, but in the specifics of what the libraries contain). |
| 01:58:35 | <scriptdevil> | :) Thanks. |
| 02:00:12 | <ddarius> | There are also a variety of parser generators, most notably happy. |
| 02:00:43 | <scriptdevil> | Also, This is my first big sized project. How do I ensure that my code remains extensibe and well spread out into modules? Are there any guides on this? Or does it come down to experience? |
| 02:01:53 | <bd_> | scriptdevil: If you start getting lost in a file, it's time to split it up :) |
| 02:02:59 | <scriptdevil> | bd_: Can I actually check out a copy of some previous compiler and keep its structure as the skeleton? |
| 02:03:20 | <shapr> | @users |
| 02:03:20 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 02:03:22 | <shapr> | aww |
| 02:03:51 | <bd_> | scriptdevil: What language are you trying to compile? It's probably best not to, just so you can have freedom in designing it, imo |
| 02:03:56 | <shapr> | Aw, I forgot happy birthday #haskell |
| 02:04:00 | <shapr> | some 4 weeks ago. |
| 02:04:11 | <scriptdevil> | bd_: They are two HDLs |
| 02:04:33 | <ddarius> | (<$) makes sense to me now |
| 02:04:54 | <vininim> | "the next haskell will be strict, but still pure" <- wut |
| 02:05:10 | <ddarius> | scriptdevil: The rules are more or less the same as other languages and programming in general. |
| 02:05:33 | <eu-prleu-peupeu1> | can i alter the abstract syntax tree in run-time in haskell ? |
| 02:05:38 | <eu-prleu-peupeu1> | like ruby :P |
| 02:05:57 | <bd_> | eu-prleu-peupeu1: nope, sorry. You could use the GHC-API to compile stuff at runtime though |
| 02:06:05 | <monochrom> | run-time? please don't. |
| 02:06:22 | <SamB> | eu-prleu-peupeu1: what? |
| 02:06:47 | <scriptdevil> | Thanks all.. Gotta rush to college :D |
| 02:06:49 | <SamB> | AST's aren't supposed to exist at runtime except in exceedingly slow implementations of lisp, or implementations of lambda calculi... |
| 02:07:23 | <vininim> | http://portal.acm.org/supp_gateway.cfm?id=1238856&type=pdf&path=%2F1240000%2F1238856%2Fsupp%2FHaskell%2Epdf&coll=GUIDE&dl=GUIDE&CFID=30248690&CFTOKEN=97968208 |
| 02:07:33 | <vininim> | what is this "next haskell" that simon talks about? |
| 02:07:35 | <ddarius> | SamB: Why should they exist in implementations of lambda calculi? |
| 02:07:38 | <bd_> | SamB: Well, you could JIT-compile the AST, and if something starts editing it, undo the compilation |
| 02:08:05 | <SamB> | ddarius: well, you know, the kind that you would use in a proof system |
| 02:08:22 | <SamB> | of course the lambda calculus isn't able to access ths |
| 02:08:26 | <SamB> | s/ths/this/. |
| 02:11:22 | <monochrom> | Self-modifying programs are a fun sports, but not a viable engineering technique. |
| 02:13:19 | <SamB> | monochrom: not at that scale, at any rate |
| 02:41:54 | <NRee1> | is there a design reason why log is base-e rather than ln? |
| 02:43:20 | <SamB> | NRee1: it's more natural |
| 02:43:23 | <SamB> | duh ;-) |
| 02:43:57 | <NRee1> | hehe |
| 02:44:03 | <SamB> | were you expecting log to be base-2? |
| 02:44:10 | <hpaste> | morrow annotated "sqlite3-amalgamation.sh" with "thanks for the advice!" at http://hpaste.org/8015#a3 |
| 02:44:10 | <NRee1> | base-10 |
| 02:44:16 | <mauke> | no, log should take two arguments |
| 02:44:20 | <mauke> | base 10 is lg |
| 02:44:38 | <SamB> | mauke: that would be REALLY confusing |
| 02:44:49 | <SamB> | lg is base-2 in Knuth's books |
| 02:44:51 | <mauke> | that's how preflex does it! |
| 02:44:55 | <mauke> | no, base 2 is ld |
| 02:45:06 | <SamB> | in knuth's books? |
| 02:45:09 | <dolio> | ACTION has never seen ld. |
| 02:45:15 | <mauke> | knuth obviously never went to my school |
| 02:45:21 | <NRee1> | ACTION has never seen lg or ld |
| 02:45:30 | <mauke> | preflex: calc ld 10 |
| 02:45:31 | <preflex> | 3.321928094887363 |
| 02:45:34 | <mauke> | now you have |
| 02:45:48 | <dolio> | I've seen lg for base 2, and log for base 10, and ln for base 3. |
| 02:46:11 | <dolio> | And, of course, log with subscript b for some other base. |
| 02:46:20 | <NRee1> | http://en.wikipedia.org/wiki/Logarithm#Bases |
| 02:46:24 | <monochrom> | base 3? :) |
| 02:46:35 | <NRee1> | so the common approach is to have log to default to base 10 ;) |
| 02:46:45 | <monochrom> | Who would use base 3, other than someone crazy like Cantor? |
| 02:48:03 | <SamB> | NRee1: only in decimal contexts |
| 02:48:10 | <SamB> | programming is not one of these |
| 02:48:15 | <dolio> | I've seen log as base 2 in stuff about algorithm analysis, too, but I suppose it usually doesn't matter there. |
| 02:48:16 | <mauke> | http://de.wikipedia.org/wiki/Logarithmus#Bezeichnungen <- |
| 02:48:32 | <SamB> | I'm fairly certain the top two contenders would be e and 2 |
| 02:49:50 | <dolio> | Although I think the papers I've read where 'log' means base 2 usually explicitly say so. |
| 02:50:07 | <NRee1> | hm wow.. i never realized that.. but in C log is base-e too |
| 02:50:23 | <monochrom> | trig uses radians. |
| 02:50:43 | <SamB> | monochrom: well, it's the natural way |
| 02:51:16 | <SamB> | ACTION is reminded of the "natural selection" sort algorithm |
| 02:52:01 | <[Justice]> | if you're doing asymptotic analysis, it shouldn't matter what the base is |
| 02:52:43 | <monochrom> | until you happen to do n^(log_b m) |
| 02:52:59 | <[Justice]> | well, true |
| 02:53:18 | <monochrom> | trick question on exam: e^ln n polynomial time or not? :) |
| 02:53:30 | <[Justice]> | yes |
| 02:55:19 | <[Justice]> | (n) is a polynomial in n |
| 02:55:57 | <ddarius> | Writing naive code is relaxing. |
| 02:56:32 | <[Justice]> | eg, fib n = fib (n - 1) + fib (n - 2) |
| 02:56:33 | <bd_> | [Justice]: Isn't copying an integer O(lg n)? |
| 02:57:04 | <monochrom> | "integer" |
| 02:57:23 | <monochrom> | This hour has 24 minutes. This integer has 24 bits. |
| 02:57:37 | <[Justice]> | copying an Int is O(1), copying an Integer is (log_100000 n) |
| 02:58:19 | <dolio> | 100000? |
| 02:58:42 | <[Justice]> | any base you like is fine, within big-O notation |
| 02:59:00 | <dolio> | Yeah. |
| 03:02:52 | <bd_> | I thought O(lg n) is sub-polynomial time? |
| 03:03:58 | <[Justice]> | it's sub-linear time |
| 03:04:26 | <[Justice]> | (k) is a polynomial in n, one of an infinite number of constant, degree-0 polynomials |
| 03:05:25 | <bd_> | It's not constant, though, since we need to copy (?) a value of unknown size |
| 03:05:41 | <bd_> | so does sub-linear (but above constant time) put it outside P? |
| 03:05:57 | <[Justice]> | Int is known size, Integer is unknown size |
| 03:06:14 | <bd_> | e^ln n <-- types were unspecified :) |
| 03:06:23 | <bd_> | also, Int is still O(lg n), with n being a constant ;) |
| 03:07:50 | <[Justice]> | class P includes all functions f such that there exists a polynomial function g such that f(j) < g(j) for all j larger than a sufficiently large k |
| 03:08:26 | <[Justice]> | if f in O(log n) then f in P |
| 03:09:03 | <[Justice]> | if f in O(1) then f in P |
| 03:09:04 | <dolio> | It doesn't depend on the value n, though. Copying 0 takes as much time as copying 2147483647. |
| 03:09:32 | <[Justice]> | n is the number of bits |
| 03:09:41 | <[Justice]> | or bytes, or words, or whatever |
| 03:09:51 | <[Justice]> | wait that's wrong |
| 03:10:04 | <dolio> | Well, that would make copying an integer O(n). |
| 03:10:06 | <[Justice]> | no, copying 0 takes less time then copying 10^100 |
| 03:10:10 | <dolio> | Or, unbounded integer. |
| 03:10:33 | <[Justice]> | the size of 0 is perhaps 1 word, whereas the size of 10^100 is multiple words |
| 03:11:08 | <dolio> | Yeah, but he was talking about Int being O(lg n). |
| 03:11:29 | <TomMD> | I there a preferred structure for bindings to C libraries? I started with a two module approach: one CBindings.hs that didn't really introduce any types beyond Foreign.C, and a Haskellized API that introduced types and used all the foreign functions. I'm considering that splitting these up was a mistake and I should introduce the haskell types earlier (i.e. declare the types and make Storable instances for them that will marshall them |
| 03:11:39 | <dolio> | Int can't represent googol. |
| 03:11:40 | <bd_> | dolio: where n is constant :P |
| 03:12:17 | <dolio> | At least, not on my machine. :) |
| 03:12:26 | <[Justice]> | Integer can represent 10^100, Int cannot ... copying Integer is O(log n) and not O(1), while copying Int is O(log n) and also O(1) |
| 03:12:37 | <TomMD> | Need a PS3, that will work out for you. |
| 03:19:19 | <Twey> | ACTION wonders vaguely why there are no n - k patterns... |
| 03:21:33 | <Chater4567> | http://www.meine-wilde-ex.net/?uid=156037 |
| 03:21:34 | <lambdabot> | Title: Meine wilde Ex!!! |
| 03:21:53 | <lament> | Chater4567: or else? |
| 03:24:55 | <Mr_Awesome> | is there perhaps a way to do this with a single list comprehension? map (\x -> [(x, y) | y <- [0..h-1]]) [0..w-1] |
| 03:25:39 | <Mr_Awesome> | > map (\x -> [(x, y) | y <- [0..2]]) [0..2] |
| 03:25:41 | <lambdabot> | [[(0,0),(0,1),(0,2)],[(1,0),(1,1),(1,2)],[(2,0),(2,1),(2,2)]] |
| 03:26:07 | <ddarius> | > range (0,2) (0,2) |
| 03:26:08 | <lambdabot> | Couldn't match expected type `(t1, t2) -> t' |
| 03:26:19 | <ddarius> | > range ((0,2), (0,2)) |
| 03:26:21 | <lambdabot> | [(0,2)] |
| 03:26:29 | <ddarius> | > range ((0,0), (2,2)) |
| 03:26:30 | <lambdabot> | [(0,0),(0,1),(0,2),(1,0),(1,1),(1,2),(2,0),(2,1),(2,2)] |
| 03:27:09 | <ddarius> | Mr_Awesome: A list comprehension always produces a list. You could nest list comprehensions but that wouldn't be doing anything different. |
| 03:27:24 | <ddarius> | map (\x -> ...) l = [... | x <- l] |
| 03:28:05 | <ddarius> | > map (\x -> map ((,) x) [0..2]) [0..2] |
| 03:28:07 | <lambdabot> | [[(0,0),(0,1),(0,2)],[(1,0),(1,1),(1,2)],[(2,0),(2,1),(2,2)]] |
| 03:28:15 | <Mr_Awesome> | ddarius: ah, i see what you mean |
| 03:28:41 | <ddarius> | > map (flip map [0..2] . (,)) [0..2] |
| 03:28:42 | <lambdabot> | [[(0,0),(0,1),(0,2)],[(1,0),(1,1),(1,2)],[(2,0),(2,1),(2,2)]] |
| 03:29:09 | <dmwit> | > [(x, y) | x <- [0..2], y <- [0..2]] |
| 03:29:10 | <lambdabot> | [(0,0),(0,1),(0,2),(1,0),(1,1),(1,2),(2,0),(2,1),(2,2)] |
| 03:29:24 | <dmwit> | > replicateM2 [0..2] |
| 03:29:24 | <lambdabot> | Not in scope: `replicateM2' |
| 03:29:28 | <dmwit> | > replicateM 2 [0..2] |
| 03:29:30 | <lambdabot> | [[0,0],[0,1],[0,2],[1,0],[1,1],[1,2],[2,0],[2,1],[2,2]] |
| 03:29:40 | <ddarius> | Now transpose. |
| 03:29:54 | <dmwit> | what? |
| 03:30:12 | <ddarius> | > transpose $ replicateM 2 [0..2] |
| 03:30:13 | <lambdabot> | [[0,0,0,1,1,1,2,2,2],[0,1,2,0,1,2,0,1,2]] |
| 03:30:51 | <gwern> | ACTION happily sends off some cabalization patches for pencilpond |
| 03:30:56 | <Mr_Awesome> | > [[(x, y) | y <- [0..2]] | x <- [0..2]] |
| 03:30:58 | <lambdabot> | [[(0,0),(0,1),(0,2)],[(1,0),(1,1),(1,2)],[(2,0),(2,1),(2,2)]] |
| 03:31:23 | <gwern> | it is a fun little GUI thing, for looking at a hyperbolic plane. imo, a lot of code for what it does (but whatever) |
| 03:31:31 | <dmwit> | > [(x,y) | [x,y] <- replicateM 2 [0..2]] |
| 03:31:35 | <lambdabot> | [(0,0),(0,1),(0,2),(1,0),(1,1),(1,2),(2,0),(2,1),(2,2)] |
| 03:43:41 | <gubagem> | why does my console app have line history |
| 03:44:28 | <Lemmih> | gubagem: Are you using readline? |
| 03:44:51 | <Lemmih> | gubagem: Or rlwrap? |
| 03:45:10 | <gubagem> | not to my knowledge |
| 03:45:27 | <gubagem> | and its in a windows xp command prompt |
| 03:45:42 | <gubagem> | im just using getLine with GHC |
| 03:47:19 | <dmwit> | I find "lying" or "confusion" the most likely explanation. |
| 03:47:53 | <Lemmih> | We shouldn't rule out divine intervention, either. |
| 03:48:11 | <gubagem> | im inside a batch file loop |
| 03:48:44 | <gubagem> | i mean its nice, but I dont know how it got there |
| 03:52:38 | <dmwit> | [r | x <- m, ...] --> m >>= \x -> [r | ...]; [r | p, ...] --> guard p >> [r | ...]; [r] --> return r |
| 03:52:41 | <dmwit> | Is this correct? |
| 03:53:43 | <Zao> | NRee1: I beat #14 now. |
| 03:54:23 | <Zao> | NRee1: I used a Map to memoize the subsequences, but ended up eating 600-some MiB memory :) |
| 03:54:28 | <NRee1> | hehe |
| 03:54:30 | <dmwit> | Zao: Project Euler? |
| 03:54:36 | <NRee1> | can you post your code? |
| 03:54:39 | <Saizan> | dmwit: yup, if x is irrefutable |
| 03:54:42 | <NRee1> | I would like to compare |
| 03:54:55 | <dmwit> | Saizan: thanks |
| 03:54:58 | <NRee1> | and hopefully learn something ^^ |
| 03:55:04 | <dmwit> | Saizan: Or wait, what? |
| 03:55:15 | <dmwit> | Oh, if x is refutable, then, let's see... |
| 03:55:45 | <dmwit> | [r | pat <- m, ...] --> m >>= \x -> case x of pat -> [r | ...]; _ -> fail "" |
| 03:55:47 | <dmwit> | Like that? |
| 03:55:52 | <Saizan> | yeah |
| 03:55:58 | <Zao> | NRee1: http://www.acc.umu.se/~zao/014.hs.html |
| 03:56:00 | <lambdabot> | Title: ~/euler/014.hs.html |
| 03:56:11 | <Zao> | NRee1: Did you finish yet? |
| 03:56:32 | <NRee1> | ya i did |
| 03:56:34 | <dmwit> | Zao: Pretty colors! |
| 03:56:40 | <dmwit> | Looks like vim's coloring. |
| 03:56:54 | <Zao> | :TOhtml is a lovely command. |
| 03:57:08 | <NRee1> | dmwit: our definition of pretty is different, but i guess it is in the eye of the beholder ;) |
| 03:57:16 | <dmwit> | Zao: Beautiful. |
| 03:57:21 | <dmwit> | Zao++ |
| 03:57:41 | <mar77a> | interesting |
| 03:57:49 | <mar77a> | i got my first karma points thanks to project euler too |
| 03:58:15 | <mar77a> | one liner is_prime function :p |
| 03:58:20 | <Zao> | Oops, forgot to use -O. |
| 03:58:36 | <hpaste> | NReed pasted "Project Euler" at http://hpaste.org/8017 |
| 03:59:19 | <dmwit> | NRee1: looks slow ;-) |
| 03:59:31 | <NRee1> | hm |
| 03:59:43 | <dons> | ah, collatz. |
| 04:00:00 | <NRee1> | ya i cant actually run it under ghci |
| 04:00:12 | <dons> | for euler stuff, i think it makes sense to compile the code. |
| 04:00:15 | <dons> | but also think hard :) |
| 04:00:16 | <NRee1> | i have to compile it otherwise i get a stack overflow |
| 04:00:28 | <dons> | right, so it depends on the strictness analyser |
| 04:00:38 | <dons> | or possibly one of the fusion rules kicking in |
| 04:00:58 | <NRee1> | so how would you guys recommend speeding this thing up? |
| 04:01:01 | <dons> | ghc -O2 --make is a good option for quick code, btw. |
| 04:01:19 | <mar77a> | hm if i do a foldr with (/) is that like a continued fraction? |
| 04:01:21 | <dmwit> | NRee1: I think a stateful calculation that keeps track of pre-computed run lengths makes sense. |
| 04:01:32 | <dmwit> | > foldr (/) z [a,b,c] |
| 04:01:37 | <lambdabot> | a / (b / (c / z)) |
| 04:01:43 | <mar77a> | mm |
| 04:01:55 | <dmwit> | So... not really. |
| 04:01:57 | <mar77a> | maybe a foldl |
| 04:01:58 | <dons> | yeah, glguy liked using a memo array for this |
| 04:02:01 | <dmwit> | But you can get it to be. |
| 04:02:04 | <NRee1> | dmwit ah I just remembered that I was going to do that, but I got lazy |
| 04:02:06 | <mar77a> | i wonder how |
| 04:02:34 | <dmwit> | > foldr (\a b -> 1 / (a + b)) z [a,b,c] |
| 04:02:36 | <lambdabot> | 1 / (a + 1 / (b + 1 / (c + z))) |
| 04:03:06 | <dons> | NRee1: what value of 'n' were you using, btw? |
| 04:03:19 | <dons> | ACTION notes hpaste is a good source of collatz implementations |
| 04:03:25 | <dons> | hey, speak of the devilish glguy |
| 04:03:28 | <NReed> | wow I cant believe I miss typed my name :S |
| 04:03:36 | <NReed> | and didnt notice till now |
| 04:03:51 | <dmwit> | '1' is a pretty bad typo for 'd'. |
| 04:04:04 | <dmwit> | I just figured it was the "away" variant of your name. =) |
| 04:04:07 | <SamB_XP> | what's your excuse? |
| 04:04:16 | <NReed> | i know :S i guess haskell for a whole day mashes your brain :) |
| 04:04:18 | <glguy> | dons, if that is your real nick |
| 04:04:18 | <lambdabot> | glguy: You have 1 new message. '/msg lambdabot @messages' to read it. |
| 04:04:23 | <glguy> | weird that you aren't identified... |
| 04:05:01 | <glguy> | I can't make changes to hpaste |
| 04:05:09 | <glguy> | so I'll just keep getting that same bug report |
| 04:05:11 | <NReed> | dons I dont get the question... |
| 04:05:12 | <glguy> | over and o ver and over ;) |
| 04:05:29 | <SamB_XP> | glguy: well, it's probably because your name is at the bottom of the page! |
| 04:05:39 | <glguy> | I can't change that either! |
| 04:05:39 | <glguy> | :) |
| 04:05:52 | <SamB_XP> | glguy: perhaps you should suggest it to whoever can |
| 04:06:09 | <mar77a> | :t foldr |
| 04:06:10 | <dons> | NReed: oh, i didn't see the [1..1000000] list, sok |
| 04:06:11 | <glguy> | its just a matter of finding a server to run the new hpaste on |
| 04:06:13 | <lambdabot> | forall a b. (a -> b -> b) -> b -> [a] -> b |
| 04:06:25 | <dons> | glguy: i think we have servers |
| 04:06:33 | <mar77a> | :t (+) |
| 04:06:35 | <lambdabot> | forall a. (Num a) => a -> a -> a |
| 04:06:39 | <shapr> | glguy: Why can't you make changes to hpaste? |
| 04:06:53 | <SamB_XP> | glguy: how much bandwidth does it use? |
| 04:06:55 | <mar77a> | :t (\a b -> 1 / (a+b)) |
| 04:06:56 | <lambdabot> | forall a. (Fractional a) => a -> a -> a |
| 04:07:06 | <mar77a> | interesting |
| 04:07:08 | <glguy> | shapr: how much bandwidth does hpaste use? |
| 04:07:11 | <shapr> | um |
| 04:07:13 | <shapr> | I haven't checked. |
| 04:07:18 | <glguy> | shapr: I don't have the right version of happs anywhere |
| 04:07:21 | <shapr> | oh |
| 04:07:36 | <glguy> | and all my machines are 64bit |
| 04:07:46 | <glguy> | so its not just a matter of building on my machine but building on someone elses |
| 04:07:50 | <shapr> | hpaste doesn't work 64bit? |
| 04:07:55 | <shapr> | oh I see |
| 04:08:00 | <glguy> | kakapo is 64 bit? |
| 04:08:03 | <shapr> | Nah |
| 04:08:09 | <shapr> | I wonder if I could upgrade it... |
| 04:08:38 | <shapr> | I'm slowly moving all my scannedinavian stuff to my desktop, now that I have a static public ip. |
| 04:08:41 | <shapr> | And it's 64 bit. |
| 04:15:13 | <dons> | this looks interesting, http://haskell.org/haskellwiki/SceneGraph |
| 04:15:14 | <lambdabot> | Title: SceneGraph - HaskellWiki |
| 04:15:30 | <dons> | conal`: "he module Graphics.SceneGraph.Reactive uses Reactive to enliven a scene. ExampleReactive.hs provides an example of this.This uses a calculator defined independantly of the GUI and is made tangible by SceneGraph." |
| 04:17:53 | <slava> | hi dons |
| 04:18:01 | <sjanssen> | @keal |
| 04:18:02 | <lambdabot> | actually it bug in math |
| 04:18:12 | <sjanssen> | oh noes |
| 04:19:18 | <dons> | heya slava |
| 04:22:58 | <thetallguy> | ACTION wonders what language dons is speaking |
| 04:28:06 | <dmwit> | heh heh heh |
| 04:28:41 | <Twey> | thetallguy: Haskell 2.0 -- it was so useful they merged it with Lojban and made it a human language. |
| 04:29:22 | <dmwit> | Dang, I can't even compute all the primes up to 5e7 in under a minute. How am I supposed to do this problem? |
| 04:30:03 | <bd_> | which problem? |
| 04:30:10 | <sjanssen> | just do it in C |
| 04:30:32 | <dmwit> | http://projecteuler.net/index.php?section=problems&id=187 |
| 04:30:33 | <lambdabot> | Title: Problem 187 - Project Euler |
| 04:30:33 | <Twey> | *chuckle* |
| 04:31:48 | <dmwit> | ACTION has trouble imagining a way to do this without computing a buttload of primes |
| 04:31:53 | <dolio> | How are you computing them? |
| 04:32:12 | <dmwit> | ?wiki primes |
| 04:32:12 | <lambdabot> | http://www.haskell.org/haskellwiki/primes |
| 04:32:32 | <dmwit> | ...not like that |
| 04:33:05 | <dmwit> | http://www.haskell.org/haskellwiki/Prime_numbers |
| 04:33:06 | <lambdabot> | Title: Prime numbers - HaskellWiki |
| 04:33:14 | <dmwit> | The one there that starts with "merge". |
| 04:34:08 | <dolio> | I used trial division and it worked for that problem. |
| 04:34:16 | <bd_> | ACTION tries implementing a sieve of eratosthenes up to 10^8 |
| 04:34:42 | <dmwit> | > 2e8 / 1024 / 1024 |
| 04:34:43 | <lambdabot> | 190.73486328125 |
| 04:35:01 | <dolio> | (And then I wrote another solution with STUArrays, but whatever. :)) |
| 04:35:01 | <dmwit> | 190 megs might not be that bad, assuming Bool will fit in two bytes. |
| 04:35:11 | <bd_> | dmwit: STUarray puts Bool on one bit, I think? |
| 04:35:14 | <bd_> | in one bit* |
| 04:35:17 | <sjanssen> | bd_: yes, it does |
| 04:35:22 | <dmwit> | It wouldn't surprise me. |
| 04:35:32 | <dmwit> | So call it 15 megs, then. |
| 04:36:01 | <dolio> | I'm pretty sure the one with trial division worked in a reasonable amount of time, though. |
| 04:36:14 | <dmwit> | Okay, time to try using naiveIsPrime, then. =) |
| 04:36:35 | <dons> | bitwise bool sieve, http://shootout.alioth.debian.org/gp4/benchmark.php?test=nsievebits&lang=ghc&id=0 |
| 04:36:36 | <lambdabot> | Title: nsieve-bits Haskell GHC program | Gentoo : Intel® Pentium® 4 Comp ..., http://tinyurl.com/2xnch4 |
| 04:37:21 | <dolio> | My solution using STUArrays apparently took some fact I learned in the comments on that problem, though. |
| 04:37:57 | <dolio> | Some way of computing the answer based on the number of primes below a given value, so it computed the answer during the prime sieve loop. |
| 04:39:35 | <dmwit> | Oh, yeah, it's (n `choose` 2) if n is the number of primes. |
| 04:39:45 | <dmwit> | But that doesn't help until you've counted the primes... |
| 04:40:27 | <dolio> | Yeah, well, my sieve had both an STUArray Int Bool for the primes and an STUArray Int Int for pi(n). |
| 04:40:28 | <dmwit> | (Well... n `choose` 2 + n, I guess.) |
| 04:40:51 | <dolio> | Or something like that. |
| 04:41:37 | <dmwit> | Oh, heh, that reduces to n(n+1)/2, which should have been the first thing I said anyway. |
| 04:41:46 | <dmwit> | It's the sum of the first 'n' naturals. |
| 04:43:04 | <dolio> | The STUArray version takes 9 - 10 seconds. I think the one with lists took a minute or two. |
| 04:43:40 | <bd_> | @hoogle STUArray |
| 04:43:41 | <lambdabot> | Data.Array.ST.STUArray :: data STUArray s i a |
| 04:43:41 | <lambdabot> | Data.Array.ST.runSTUArray :: Ix i => ST s (STUArray s i e) -> UArray i e |
| 04:43:41 | <lambdabot> | Data.Array.ST.castSTUArray :: STUArray s ix a -> ST s (STUArray s ix b) |
| 04:46:20 | <dmwit> | This naive version definitely isn't going to make it in under a minute. |
| 04:46:45 | <dmwit> | It barely got up to 15,000 in a minute. |
| 04:51:47 | <bd_> | woo, got the answer in 46.12 seconds :3 |
| 04:52:12 | <bd_> | (runtime, not thinking time :) |
| 04:52:20 | <ddarius> | Hmm. Lollimon parses ! ! a, but the paper suggests that that isn't syntactically valid (in a sense ! : A -> S) |
| 04:56:07 | <dmwit> | bd_: ghci or ghc? |
| 04:58:08 | <bd_> | dmwit: ghc -O2, native code generator |
| 04:58:19 | <dmwit> | Oh, okay. |
| 04:58:42 | <dmwit> | I don't feel so bad, then, as the primes generator I already have can solve it in 145s under -O2. |
| 04:59:09 | <dmwit> | If you were getting 46s in ghci, I would have been way less happy. =P |
| 04:59:19 | <ddarius> | Wait. It seems to be in the wrong syntactic class altogether. |
| 04:59:41 | <mbz> | bd_, what kind of cpu do you have? |
| 04:59:59 | <bd_> | mbz: AMD Turion(tm) 64 X2 Mobile Technology TL-50 |
| 05:00:08 | <bd_> | I did not attempt to paralleize it, and it's running in 32-bit mode |
| 05:03:35 | <ddarius> | well shit |
| 05:06:34 | <nolrai_> | :t (&&&) |
| 05:06:36 | <lambdabot> | forall (a :: * -> * -> *) b c c'. (Arrow a) => a b c -> a b c' -> a b (c, c') |
| 05:07:53 | <nolrai_> | > :t curry |
| 05:07:54 | <lambdabot> | parse error on input `:' |
| 05:08:01 | <nolrai_> | :t curry |
| 05:08:03 | <lambdabot> | forall a b c. ((a, b) -> c) -> a -> b -> c |
| 05:08:52 | <nolrai_> | :t \f g -> curry (uncurry f &&& uncurry g) |
| 05:08:54 | <lambdabot> | forall a b c c1. (a -> b -> c) -> (a -> b -> c1) -> a -> b -> (c, c1) |
| 05:09:39 | <nolrai_> | meh |
| 05:09:54 | <cdsmithus> | There seem to be several different ways to do exceptions in Haskell. Which one should I mention to new Haskell programmers? |
| 05:10:20 | <ddarius> | It depends on your goals. |
| 05:10:34 | <cdsmithus> | My goal is to stick a slide in this presentation about exceptions |
| 05:11:25 | <ddarius> | Then any exception mechanism can be described on a slide and put into your presentation. |
| 05:11:58 | <cdsmithus> | Yeah, I was just wondering is there's some conventional wisdom; like avoid ioError and use Control.Exception, or vice versa |
| 05:12:33 | <ddarius> | Again, it depends on your goals. What do you want the audience to get out of your slide? |
| 05:13:02 | <SamB_XP> | I would mention Exception |
| 05:13:38 | <cdsmithus> | ddarius, that's a good question. I honestly don't know at this point. It just seems like something I should mention, even though I've never had a reason to use it. |
| 05:14:22 | <SamB_XP> | why mention it if you don't use it? |
| 05:14:22 | <dmwit> | If you just want to cover error-handling, and have a Haskell-ish way of doing it, why not just show MonadError? |
| 05:15:22 | <cdsmithus> | Hmm. I already am talking about the Maybe monad. Maybe I'll just take exceptions out. |
| 05:18:03 | <nolrai_> | that might be best. |
| 05:18:22 | <ddarius> | ACTION needs to consider the laws of the monad. |
| 05:18:54 | <SamB_XP> | cdsmithus: or talk about Either instead ;-) |
| 05:19:05 | <glguy> | dons: github is pretty awesome |
| 05:19:05 | <glguy> | I'm going to have to give you a demo when I get back |
| 05:20:33 | <ddarius> | :t (. return) |
| 05:20:35 | <lambdabot> | forall b a (m :: * -> *). (Monad m) => (m a -> b) -> a -> b |
| 05:20:59 | <ddarius> | That's the secret. |
| 05:21:59 | <ddarius> | I think... |
| 05:23:21 | <nolrai_> | thats a weird type, what are you doing? |
| 05:24:36 | <ddarius> | Trying to understand why ! a -o b is legal in the CLF/Lollimon when S ::= A | ! A | ... and A ::= A -o A | { S } | ... |
| 05:24:58 | <ddarius> | Where { _ } represents a monad type constructor. |
| 05:25:28 | <ddarius> | Where (! a -o b) means ((! a) -o b) |
| 05:38:24 | <nolrai_> | :t guard |
| 05:38:26 | <lambdabot> | forall (m :: * -> *). (MonadPlus m) => Bool -> m () |
| 05:40:33 | <bd_> | @hoogle compareBy |
| 05:40:33 | <lambdabot> | No matches found |
| 05:40:40 | <bd_> | :t soryBy |
| 05:40:42 | <bd_> | :t sortBy |
| 05:40:42 | <lambdabot> | Not in scope: `soryBy' |
| 05:40:43 | <lambdabot> | forall a. (a -> a -> Ordering) -> [a] -> [a] |
| 05:41:00 | <nolrai_> | > [guard (x > 3) >> return $ show x | x <- [0..7]] |
| 05:41:01 | <lambdabot> | add an instance declaration for (Show (m String)) |
| 05:41:14 | <nolrai_> | > [guard (x > 3) >> return $ x | x <- [0..7]] |
| 05:41:15 | <lambdabot> | add an instance declaration for (MonadPlus ((->) a)) |
| 05:41:31 | <nolrai_> | > [guard (x > 3) >> return x | x <- [0..7]] |
| 05:41:32 | <lambdabot> | add an instance declaration for (Show (m t)) |
| 05:42:26 | <nolrai_> | > do {x <- [0..6]; guard (x > 3); return (x * 2)} |
| 05:42:28 | <lambdabot> | [8,10,12] |
| 05:43:33 | <nolrai_> | :t fail |
| 05:43:35 | <lambdabot> | forall (m :: * -> *) a. (Monad m) => String -> m a |
| 05:44:15 | <nolrai_> | @src State fail |
| 05:44:15 | <lambdabot> | Source not found. I've seen penguins that can type better than that. |
| 05:44:23 | <nolrai_> | @src fail |
| 05:44:23 | <lambdabot> | fail s = error s |
| 05:46:14 | <ddarius> | :t (=<<) |
| 05:46:15 | <lambdabot> | forall a (m :: * -> *) b. (Monad m) => (a -> m b) -> m a -> m b |
| 05:47:11 | <Twey> | @pl \x y -> (y, x + y) |
| 05:47:11 | <lambdabot> | ap (,) . (+) |
| 05:49:19 | <nolrai_> | :t (>==) |
| 05:49:20 | <lambdabot> | Not in scope: `>==' |
| 05:49:26 | <nolrai_> | :t (<==) |
| 05:49:27 | <lambdabot> | Not in scope: `<==' |
| 05:49:34 | <dmwit> | :t ==> |
| 05:49:36 | <lambdabot> | parse error on input `==>' |
| 05:49:38 | <dmwit> | :t (==>) |
| 05:49:40 | <lambdabot> | forall a. (Testable a) => Bool -> a -> Property |
| 05:50:02 | <nolrai_> | ? |
| 05:50:13 | <nolrai_> | @src ==> |
| 05:50:13 | <lambdabot> | Source not found. Just what do you think you're doing Dave? |
| 05:50:28 | <dmwit> | ?check \n -> even n ==> 2 * (n `div` 2) == n |
| 05:50:29 | <lambdabot> | OK, passed 500 tests. |
| 05:50:37 | <dmwit> | ?check \n -> 2 * (n `div` 2) == n |
| 05:50:38 | <lambdabot> | Falsifiable, after 1 tests: 1 |
| 05:50:53 | <nolrai_> | impiles? |
| 05:51:00 | <dmwit> | yes |
| 05:52:56 | <nolrai_> | is there a standard symbol for cobind? |
| 05:53:06 | <dmwit> | =>>, I think |
| 05:55:25 | <dmwit> | Will it be faster to readArray multiple times, or (!) multiple times? |
| 05:55:59 | <dmwit> | i.e. if I'm going to be in the ST monad anyway, should I bother runSTUArray'ing the part of the computation that's done? |
| 05:56:29 | <mbz> | dmwit, why not to test it? |
| 05:56:35 | <dmwit> | right |
| 05:58:26 | <dmwit> | :t unfoldr |
| 05:58:28 | <lambdabot> | forall b a. (b -> Maybe (a, b)) -> b -> [a] |
| 06:00:02 | <dmwit> | :t accumArray |
| 06:00:04 | <lambdabot> | forall e a i. (Ix i) => (e -> a -> e) -> e -> (i, i) -> [(i, a)] -> Array i e |
| 06:10:52 | <ddarius> | :t (ap .) . join |
| 06:10:53 | <lambdabot> | forall (m :: * -> *) a b (m1 :: * -> *). (Monad m1, Functor m1, Monad m) => m1 (m1 (m (a -> b))) -> m1 (m a -> m b) |
| 06:11:08 | <ddarius> | :t (join .) . ap |
| 06:11:10 | <lambdabot> | forall a (m :: * -> *) a1. (Monad m) => m (a1 -> m a) -> m a1 -> m a |
| 06:11:25 | <ddarius> | :t (join .) . (=<<) |
| 06:11:26 | <lambdabot> | forall a a1 (m :: * -> *). (Monad m) => (a1 -> m (m a)) -> m a1 -> m a |
| 06:11:34 | <ddarius> | :t (join .) . (>>=) |
| 06:11:36 | <lambdabot> | forall a (m :: * -> *) a1. (Monad m) => m a1 -> (a1 -> m (m a)) -> m a |
| 06:12:11 | <ddarius> | \mf a -> mf >>= ($ a) |
| 06:12:19 | <ddarius> | :t \mf a -> mf >>= ($ a) |
| 06:12:20 | <lambdabot> | forall (m :: * -> *) a b. (Monad m) => m (a -> m b) -> a -> m b |
| 06:20:19 | <nolrai_> | @src join |
| 06:20:20 | <lambdabot> | join x = x >>= id |
| 06:28:27 | <dons> | there you go, http://reddit.com/r/programming/info/6ll73/comments/ |
| 06:28:34 | <dons> | "hsXenCtrl: script Xen with Haskell" |
| 06:28:43 | <dons> | good to see new areas being pushed on. |
| 06:28:51 | <dons> | the scenegraph lib released today also looks interesting |
| 06:31:30 | <gwern> | ACTION reads about the [[American flag sort]] |
| 06:32:11 | <dons> | dcoutts: this one might be for you, "Subject: [Haskell-cafe] Images and GUIs in Haskell" |
| 06:32:18 | <dons> | ACTION does triage on the mailing list |
| 06:32:43 | <dons> | hmm. i wonder if triage for community help has been written down before. |
| 06:33:06 | <dons> | we could have little forms like this, http://upload.wikimedia.org/wikipedia/commons/9/97/Deconference-2002-triage-tag.jpg |
| 06:33:07 | <lambdabot> | http://tinyurl.com/5k5jro |
| 06:33:09 | <dons> | :) |
| 06:33:23 | <dons> | "Stack overflow: Yes/No" |
| 06:33:30 | <dons> | "Forgot --make" |
| 06:33:39 | <dons> | "Andrew Coppin" |
| 06:33:58 | <dons> | "Blunt object trauma inflicted by GHC" |
| 06:35:52 | <dmwit> | "Function is monomorphic, but should be polymorphic" |
| 06:36:09 | <dmwit> | "Don't understand $!@% about monads" |
| 06:36:15 | <dons> | heh |
| 06:36:28 | <dons> | a top 10 FAQs would be useful |
| 06:36:36 | <dons> | lots of projects have FAQs, why not haskell |
| 06:36:51 | <dons> | "How do I catch the exception that 'read' throws" |
| 06:37:53 | <dmwit> | "Disenchanted because I have to tell compiler how to parallelize my code" |
| 06:38:27 | <dmwit> | Actually, that's not such an FAQ. |
| 06:40:46 | <dons> | well, its that general theme of wtf, i thought haskell could do parallel for me!? |
| 06:41:06 | <dons> | "Is Haskell just for mathematicians?" |
| 06:41:12 | <araujo> | No! |
| 06:42:14 | <proqesi> | sure |
| 06:42:15 | <dancor> | my biggest problem is that i feel _slow_ in haskell |
| 06:42:41 | <proqesi> | and C is just for OS designers |
| 06:43:04 | <ddarius> | dons: There was a FAQ on the old wiki. |
| 06:43:23 | <dancor> | maybe because every time you do a hack to save time, haskell makes you feel really bad about it, like you killed a puppy |
| 06:44:10 | <Twey> | Hahahahaha |
| 06:44:19 | <dmwit> | Hum, how can a run to STUArrays at once? |
| 06:44:29 | <dons> | hmm, we need a "haskell really damn fast" do we? |
| 06:44:33 | <dmwit> | Do I have to have an STUArray of a pair? |
| 06:44:36 | <dons> | for just getting the job done. |
| 06:44:46 | <dons> | dmwit: hmm, you can allocate inside a runST |
| 06:44:47 | <atp> | you can most likely have two stuarrays |
| 06:44:49 | <dons> | as many as you need |
| 06:44:59 | <dons> | just ask for a newArray |
| 06:45:05 | <dmwit> | right... |
| 06:45:25 | <atp> | the ST monad is sort of a pain |
| 06:45:26 | <dmwit> | So I can get (ST s (STUArray a, STUArray b)). |
| 06:45:31 | <dmwit> | (schematically) |
| 06:45:34 | <dmwit> | Then what? |
| 06:46:01 | <dmwit> | runST gets me a pair of STUArrays, but I can't really see any operations that take straight STUArrays. |
| 06:46:12 | <dolio> | You'd want to freeze them. |
| 06:46:31 | <dolio> | And get 'ST s (UArray a, UArray b)'. |
| 06:46:33 | <dmwit> | Ah, freeze operates on all instances of MArray. |
| 06:46:45 | <dmwit> | Sweet, thanks. |
| 06:53:20 | <dmwit> | ?index newSTRef |
| 06:53:20 | <lambdabot> | Data.STRef.Lazy, Data.STRef, Data.STRef.Strict |
| 07:00:21 | <dmwit> | ?index UArray |
| 07:00:21 | <lambdabot> | Data.Array.Unboxed |
| 07:13:39 | <dmwit> | hum |
| 07:13:51 | <dmwit> | :t ST.runSTUArray $ createFactorCounts 10 -- gives an error |
| 07:13:57 | <lambdabot> | Couldn't find qualified module. |
| 07:14:17 | <dmwit> | :t ST.runSTUArray $ createFactorCounts 10 :: UA.UArray Int Int -- does not give an error |
| 07:16:46 | <Lemmih> | dmwit: createFactorCounts is too general? |
| 07:17:42 | <dmwit> | I guess so, but I don't understand how or why. |
| 07:18:20 | <dmwit> | I thought the big idea of HM type systems was that anything that has some valid type has an automatically-inferrable most general type. |
| 07:27:14 | <nolrai_> | what does "the eta-reduction property does not hold" mean in an erro about newtype deriving? |
| 07:27:27 | <nolrai_> | s/erro/error |
| 07:28:16 | <nolrai_> | never mind i think i got it. |
| 07:31:00 | <Twey> | nolrai_: That's one scary-lookin' error you got there, sonny-Jim... O.O |
| 08:02:01 | <kaol> | I'm trying to come up with a way to write code that can both generate XSLT and apply it to a haskell data structure and generate XML. Fun stuff. |
| 08:03:58 | <kaol> | trying to include some sort of caching logic with those document() XSL functions too |
| 08:05:37 | <int-e> | hGetContents-- |
| 08:44:57 | <quicksilver> | int-e++ |
| 08:49:42 | <Saul_> | I'm having some problems installing hsql 1.7 |
| 08:49:45 | <Saul_> | Could not find module `System.Time': |
| 08:49:45 | <Saul_> | it is a member of package old-time-1.0.0.0, which is hidden |
| 08:50:48 | <Saul_> | Does anyone know how to fix this? |
| 08:51:22 | <quicksilver> | it means hsql hasn't been ported to 6.8.2 I think |
| 08:51:33 | <quicksilver> | you can try adding old-time to the depends in the cabal |
| 08:51:40 | <quicksilver> | and keep adding any more packages it complains about |
| 08:53:26 | <Saul_> | Ok I'll try it |
| 08:56:28 | <Saul_> | ok I think I got it |
| 08:56:53 | <Saul_> | I also got a compile error, but adding -fglasgow-exts solved it |
| 08:59:18 | <Saul_> | Hmmz now I get this error while configuring hsql-mysql |
| 08:59:20 | <Saul_> | Setup.lhs:8:33: |
| 08:59:20 | <Saul_> | Module |
| 08:59:20 | <Saul_> | `Distribution.Simple.Utils' |
| 08:59:20 | <Saul_> | does not export |
| 08:59:21 | <Saul_> | `rawSystemVerbose' |
| 09:02:47 | <Saul_> | Oh great it even says so on the hackage page |
| 09:02:48 | <Saul_> | http://hackage.haskell.org/cgi-bin/hackage-scripts/package/hsql-mysql |
| 09:02:50 | <lambdabot> | http://tinyurl.com/5khq9n |
| 09:19:19 | <Saul_> | Argh, I figured I would use HDBC sqlite instead, and I get different weird errors :( |
| 09:20:32 | <Heffalump> | I use hsql-mysql with ghc 6.8.2, but I can't remember if I had to make any local changes |
| 09:21:14 | <Heffalump> | hmm, none that I can find |
| 09:26:22 | <Saul_> | :( |
| 09:30:28 | <Saul_> | It seems like the Setup.lhs file itself is containing compile errors |
| 09:31:09 | <Saul_> | I took out the explicit import of rawSystemVerbose (it's not even used) but now I got other errors that are less easy to solve |
| 09:35:20 | <Heffalump> | which cabal are you using? |
| 09:36:58 | <Heffalump> | you might want to build from the darcs repo at http://code.haskell.org/HSQL/ instead |
| 09:36:58 | <lambdabot> | Title: Index of /HSQL |
| 09:41:01 | <Saul_> | I'm using Cabal-1.2.3.0 |
| 09:41:46 | <Saul_> | which appears to be the newest version |
| 09:41:55 | <Heffalump> | for 6.8.2, yeah |
| 09:42:08 | <Heffalump> | try that darcs repo for HSQL, I'm fairly sure I've built it ok from that |
| 09:43:08 | <Saul_> | ok |
| 09:44:50 | <Saul_> | Setup.lhs:9:7: |
| 09:44:50 | <Saul_> | Could not find module `Distribution.PackageDescription.Parse': |
| 09:44:50 | <Saul_> | Use -v to see a list of the files searched for. |
| 09:44:57 | <Saul_> | different error :) |
| 09:48:37 | <Heffalump> | Wed Apr 16 06:56:15 BST 2008 marco-oweber@gmx.de |
| 09:48:38 | <Heffalump> | * fixed verbose flag FIXME in Setup.lhs of MySQL |
| 09:48:40 | <Heffalump> | unpull that patch |
| 09:50:44 | <Saul_> | Heffalump: How do I use unpull to unpull that patch? |
| 09:50:58 | <Saul_> | I'm not that savy with darcs yet |
| 09:51:01 | <dmwit> | darcs unpull -p "verbose flag FIXME" |
| 09:55:50 | <Saul_> | ok that seemed to work, thanks dmwit and Heffalump |
| 10:12:26 | <mxc_> | is anyone here familiar with Data.Binary and laziness? |
| 10:12:47 | <mxc_> | quesiton is, if i have a tuple (x,y) that I decode |
| 10:13:05 | <mxc_> | say data MyTup = MyTup (x,y) |
| 10:13:26 | <mxc_> | and in the get implementation, the data for x is read frist, if I never reference y, will it just lazily ignore it? |
| 10:13:45 | <Twey> | Yep |
| 10:14:22 | <mxc_> | cool, so in my situation, x is a single word8 which functions use to determine if they want to decode y (some big ugly record) |
| 10:14:33 | <mxc_> | speed is important so i only want to decode y when necessary |
| 10:15:22 | <mxc_> | thanks twey |
| 10:16:09 | <Twey> | Welcome |
| 10:16:16 | <Heffalump> | the downside of it being lazily ignored is that the source data will hang around as long as references to y do |
| 10:18:34 | <MedeaMelana> | morning |
| 10:26:19 | <flippo> | preflex, be poppavic |
| 10:26:19 | <preflex> | dude, you need to stop hollering and either spend more verbage explaining it to them or just DON'T. |
| 10:26:32 | <flippo> | (Sorry.) |
| 10:34:51 | <vixey> | Heffalump, why ban it? |
| 10:35:29 | <Twey> | Wasn't the real IRSeekBot |
| 10:38:31 | <MedeaMelana> | it's quiet today |
| 10:40:17 | <vixey> | > let f91 x | x > 100 = x - 10 | otherwise = f91 . f91 $ x + 11 in map f91 [1..] |
| 10:40:19 | <lambdabot> | [91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,91,... |
| 10:41:28 | <MedeaMelana> | does that work for other numbers than -10 too? |
| 10:43:36 | <Heffalump> | vixey: I assumed it was up to something nefarious, given the number of times it's flooded itself of |
| 10:43:41 | <MedeaMelana> | > let f91 x | x > 100 = x - 9 | otherwise = f91 . f91 $ x + 11 in map f91 [1..] |
| 10:43:42 | <Heffalump> | do you know something about it? |
| 10:43:43 | <lambdabot> | [92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,93,92,... |
| 10:44:09 | <mercury^> | MedeaMelana: maybe you have to adjust teh +11 too |
| 10:45:14 | <MedeaMelana> | > let f91 x | x > 100 = x - 9 | otherwise = f91 . f91 $ x + 10 in map f91 [1..] |
| 10:45:15 | <lambdabot> | [92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,... |
| 10:45:24 | <MedeaMelana> | hmm |
| 10:46:13 | <nornagon> | > repeat 92 |
| 10:46:14 | <lambdabot> | [92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,92,... |
| 10:46:21 | <MedeaMelana> | Something else I've been wondering about: why isn't ($) defined as id, with type a -> a ? |
| 10:46:30 | <nornagon> | @src ($) |
| 10:46:30 | <lambdabot> | f $ x = f x |
| 10:46:35 | <vixey> | MedeaMelana: that's a valid definition |
| 10:46:46 | <MedeaMelana> | :t ($) |
| 10:46:48 | <lambdabot> | forall a b. (a -> b) -> a -> b |
| 10:46:52 | <MedeaMelana> | :t id |
| 10:46:54 | <lambdabot> | forall a. a -> a |
| 10:46:58 | <vixey> | MedeaMelana: (a -> b) -> a -> b is more descriptive though |
| 10:47:17 | <MedeaMelana> | yes, more descriptive, more restrictive |
| 10:47:26 | <nornagon> | more restrictive? |
| 10:47:27 | <nornagon> | how? |
| 10:47:32 | <vixey> | it's not a restriction |
| 10:47:35 | <vixey> | id still exists |
| 10:47:44 | <nornagon> | a -> a is a subset of a -> b |
| 10:48:05 | <MedeaMelana> | > head `id` [1..] |
| 10:48:06 | <lambdabot> | 1 |
| 10:48:10 | <MedeaMelana> | > head $ [1..] |
| 10:48:12 | <lambdabot> | 1 |
| 10:48:22 | <vixey> | > id 3 |
| 10:48:23 | <lambdabot> | 3 |
| 10:48:24 | <vixey> | > ($) 3 |
| 10:48:24 | <lambdabot> | add an instance declaration for (Num (a -> b)) |
| 10:48:42 | <MedeaMelana> | yes, that makes it more restrictive, I think |
| 10:48:47 | <MedeaMelana> | id does everything $ does |
| 10:48:48 | <nornagon> | ah, right. |
| 10:49:05 | <vixey> | id has a more general type |
| 10:49:16 | <nornagon> | sry, not thinking :P |
| 10:49:41 | <mercury^> | MedeaMelana: you can force the type of something with $ |
| 10:49:56 | <MedeaMelana> | Yes. Why is that useful here? |
| 10:50:20 | <vixey> | > map ($ 3) [(+3), (*2)] |
| 10:50:21 | <lambdabot> | [6,6] |
| 10:50:41 | <mercury^> | MedeaMelana: I had a good example where you needed $ and could not use id |
| 10:50:46 | <mercury^> | now I just need to remember it |
| 10:50:48 | <mercury^> | -.- |
| 10:50:57 | <MedeaMelana> | Maybe vixey's example works? |
| 10:51:03 | <vixey> | mercury^: I don't think that it exists |
| 10:51:09 | <nornagon> | > map (`id` 3) [(+3),(*2)] |
| 10:51:10 | <MedeaMelana> | > map (`id` 3) [(+3), (*2)] |
| 10:51:10 | <lambdabot> | [6,6] |
| 10:51:11 | <lambdabot> | [6,6] |
| 10:51:14 | <vixey> | :t id :: (a -> b) -> a -> b |
| 10:51:16 | <lambdabot> | forall a b. (a -> b) -> a -> b |
| 10:51:16 | <nornagon> | :D |
| 10:52:11 | <MedeaMelana> | I realized a while ago that $ is id for functions, but I never realized that it actually *is* id |
| 10:52:21 | <vixey> | currying |
| 10:52:24 | <Heffalump> | well, it's not because of the type |
| 10:52:37 | <Heffalump> | The only reason I can think of for restricting the type is to improve error messages |
| 10:52:50 | <MedeaMelana> | That's a good reason |
| 10:52:50 | <vixey> | I think the type is documentation |
| 10:53:47 | <Heffalump> | I can't think of a good example of it actually improving an error message in any sensible use, though. |
| 10:54:13 | <vixey> | and f $ x = f x describes its use much better than ($) = id |
| 10:54:16 | <MedeaMelana> | You have to misuse $ before you get any error messages |
| 10:54:30 | <MedeaMelana> | How could one misuse $ |
| 10:54:39 | <vixey> | > 7 * ($) |
| 10:54:39 | <lambdabot> | add an instance declaration for (Num ((a -> b) -> a -> b)) |
| 10:54:48 | <MedeaMelana> | I mean, what are understandable ways to misuse $ |
| 10:54:55 | <vixey> | there aren't any |
| 10:55:07 | <vixey> | any badly typed expression is nonsens |
| 10:55:39 | <MedeaMelana> | What I mean is: some mistakes are easily made and very common. |
| 10:55:47 | <MedeaMelana> | At least for those who are new to Haskell. |
| 10:56:16 | <Heffalump> | I meant "any sensible misuse" |
| 10:56:22 | <vixey> | > let f91 x | x > 100 = x - 10 | otherwise = f91 . f91 $ x + 11 in drop 95 (map f91 [1..]) |
| 10:56:24 | <lambdabot> | [91,91,91,91,91,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,1... |
| 10:56:26 | <Heffalump> | i.e. any code that someone might reasonably be trying to write, but got wrong |
| 10:56:37 | <MedeaMelana> | Exactly |
| 10:57:01 | <MedeaMelana> | Of course, there's normal misapplication of arguments to functions, and the programmer might have used $ there |
| 10:57:41 | <Heffalump> | the thing is, as soon as you use it as a fully-applied infix operator, its type is forced to the function type anyway |
| 10:57:46 | <Heffalump> | since that's the only way it can take two arguments |
| 10:58:04 | <Heffalump> | so a "sensible misuse" would have to use it as a sectioned operator somehow |
| 10:58:25 | <vixey> | any misuse of ($) will look like nonsense |
| 10:58:33 | <MedeaMelana> | > head True |
| 10:58:34 | <lambdabot> | Couldn't match expected type `[a]' against inferred type `Bool' |
| 10:58:40 | <vixey> | just like 7 * ($) |
| 10:58:40 | <MedeaMelana> | > head $ True |
| 10:58:40 | <lambdabot> | Couldn't match expected type `[a]' against inferred type `Bool' |
| 10:58:46 | <MedeaMelana> | > head `id` True |
| 10:58:47 | <lambdabot> | Couldn't match expected type `Bool' against inferred type `[a]' |
| 10:58:53 | <MedeaMelana> | hehe |
| 10:59:07 | <Heffalump> | vixey: I'm not completely convinced of that, but I certainly can't think of any good examples to contradict it. |
| 10:59:25 | <Heffalump> | MedeaMelana: ok, that's actually halfway decent |
| 10:59:26 | <vixey> | *any* badly typed expression is complete nonsense |
| 10:59:33 | <Heffalump> | vixey: oh, now that is rubbish |
| 10:59:44 | <Heffalump> | a simple error can move you from a well-typed expression to an ill-typed one |
| 10:59:46 | <vixey> | if it doesn't type the expression has no meanin |
| 11:00:05 | <Heffalump> | the question is how well the implementation does at explaining what is wrong to the user |
| 11:00:12 | <vixey> | :t 2 ^ 0.5 |
| 11:00:14 | <lambdabot> | Ambiguous type variable `t' in the constraints: |
| 11:00:14 | <lambdabot> | `Integral t' arising from a use of `^' at <interactive>:1:0-6 |
| 11:00:14 | <lambdabot> | `Fractional t' |
| 11:00:23 | <vixey> | this -doesn't- take the square root of two |
| 11:00:25 | <Heffalump> | MedeaMelana: because there's nothing in head $ True that has type [a], so it's a bit odd to see it being inferred for something. |
| 11:02:21 | <MedeaMelana> | vixey: the question is whether $'s current (restrictive) type could ever improve the quality of error messages |
| 11:02:41 | <MedeaMelana> | apart from the fact that it's current type describes its common use better |
| 11:02:48 | <MedeaMelana> | its* |
| 11:02:51 | <vixey> | > ($) 3 |
| 11:02:52 | <lambdabot> | add an instance declaration for (Num (a -> b)) |
| 11:03:41 | <Heffalump> | that's a nice example too |
| 11:04:03 | <MedeaMelana> | i'm not sure what that shows |
| 11:04:20 | <Heffalump> | > id 3 |
| 11:04:21 | <lambdabot> | 3 |
| 11:04:21 | <vixey> | it's at type error I got from misuse of ($) |
| 11:04:29 | <Heffalump> | it provides an error that you wouldn't have got from id |
| 11:04:34 | <Heffalump> | which is useful |
| 11:04:45 | <Heffalump> | > id 3 2 |
| 11:04:45 | <lambdabot> | add an instance declaration for (Num (t -> a)) |
| 11:04:49 | <Heffalump> | > ($) 3 2 |
| 11:04:50 | <lambdabot> | add an instance declaration for (Num (a -> b)) |
| 11:04:57 | <vixey> | anyway the real reason ($) :: (a -> b) -> a -> b is documentation as I said before |
| 11:05:20 | <MedeaMelana> | probably |
| 11:05:20 | <Heffalump> | do you actually know this from a historical perspective, or are you just guessing? |
| 11:05:29 | <MedeaMelana> | which i'm not sure is a good enough reason |
| 11:05:33 | <vixey> | it suggests: ((foo :: a -> b) $ (bar :: a)) :: b |
| 11:11:23 | <kowey> | ?seen gour |
| 11:11:23 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 11:11:43 | <Heffalump> | I guess it's database is broken |
| 11:11:49 | <Heffalump> | s/it's/its/ |
| 11:12:09 | <kowey> | hmm... yeah, just signaling the problem |
| 11:22:43 | <MedeaMelana> | I think it'd be pretty fun if everywhere I wrote id I could write ($) instead :-) |
| 11:23:12 | <MedeaMelana> | Though id is a better name for identity |
| 11:23:47 | <Baughn> | $ does have the distinct advantage of being slicable |
| 11:24:05 | <Baughn> | map (`id` 42) [(+1)] just doesn't have the same feel. ;) |
| 11:24:16 | <Baughn> | > map (`id` 42) [(+1)] -- does it even work? |
| 11:24:17 | <lambdabot> | [43] |
| 11:24:23 | <MedeaMelana> | What does slicable mean here? |
| 11:24:53 | <Baughn> | ($ 42) <- There. A slice. Unless of course I completely forgot the right word to use. |
| 11:25:07 | <Deewiant> | a section, I believe, is the standard term. |
| 11:25:20 | <MedeaMelana> | Ah, right |
| 11:25:21 | <Baughn> | Right you are |
| 11:25:40 | <MedeaMelana> | Maybe $ is more easy to optimize if it is restricted to functions? |
| 11:28:16 | <Baughn> | @type id |
| 11:28:18 | <lambdabot> | forall a. a -> a |
| 11:28:23 | <Baughn> | @type `id` 42 |
| 11:28:25 | <lambdabot> | parse error on input ``' |
| 11:28:29 | <Baughn> | @type (`id` 42) |
| 11:28:30 | <MedeaMelana> | you need () |
| 11:28:31 | <lambdabot> | forall t t1. (Num t) => (t -> t1) -> t1 |
| 11:30:24 | <MedeaMelana> | Because most (non-section) uses of $ can be trivially rewritten to an expression with $ but with more parentheses. Which might save a reduction? |
| 11:30:52 | <MedeaMelana> | I meant without $ |
| 11:31:27 | <Baughn> | The optimizer does a fine job. Don't worry about it. |
| 11:31:41 | <MedeaMelana> | That doesn't help |
| 11:34:56 | <Saul_> | @seen shapr |
| 11:34:56 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 11:35:08 | <Saul_> | awesome |
| 11:35:52 | <maltem___> | Do I remember incorrectly, or wouldn't ($) having the general type of id :: a -> a be impossible in Haskell98? |
| 11:36:22 | <mattam> | @type flip id |
| 11:36:24 | <lambdabot> | forall b c. b -> (b -> c) -> c |
| 11:36:35 | <Philippa_> | MedeaMelana: if you're working with purely unoptimised implementations then yes, $ is slower. Any compiler that can do inlining will inline something as small as $ though |
| 11:36:35 | <lambdabot> | Philippa_: You have 1 new message. '/msg lambdabot @messages' to read it. |
| 11:36:46 | <Baughn> | @dict-all pulchritudinous |
| 11:36:46 | <lambdabot> | Unknown command, try @list |
| 11:37:37 | <MedeaMelana> | Yes, so what I was asking is: maybe inlining $ is easier if it has type (a -> b) -> a -> b instead of a -> a |
| 11:38:01 | <MedeaMelana> | But I guess that doesn't make much sense |
| 11:39:08 | <Baughn> | It gets inferred down to a concrete type either way |
| 11:47:24 | <ziman> | @pl \f -> f x1 x2 |
| 11:47:25 | <lambdabot> | flip ($ x1) x2 |
| 11:47:49 | <Saul_> | is there any decent documentation out there for either haskelldb or hsql (in a tutorial-like fashion)? |
| 11:48:16 | <Saul_> | and are they mature enough to use, or should I use something else? |
| 11:49:05 | <Baughn> | I've done fine with just hdbc |
| 11:49:45 | <Baughn> | (hsql lacks parametrized queries. Don't use it.) |
| 11:53:12 | <MedeaMelana> | ACTION waves |
| 11:57:42 | <Heffalump> | as long as you're careful about SQL injection, parameterized queries are just an efficiency concern |
| 11:57:53 | <jeffz> | http://reddit.com/r/prolog/info/6llqb/comments/ might be of general interest to people - "A Wake Up Call for the Logic Programming Community", Haskell is mentioned a few times |
| 12:02:13 | <opqdonut> | hmm |
| 12:02:25 | <xci> | mmh |
| 12:04:59 | <augustss> | mhm |
| 12:06:45 | <mattam> | hmm |
| 12:06:54 | <ivanm> | mmh? |
| 12:07:04 | <ivanm> | oh, what, xci already did that one |
| 12:07:24 | <Heffalump> | no, xci did the other one |
| 12:07:39 | <Heffalump> | mhm |
| 12:07:44 | <Heffalump> | now we're done |
| 12:07:50 | <augustss> | i did that one |
| 12:07:52 | <ivanm> | no, xci did mmh... |
| 12:07:59 | <ivanm> | and opqdonut beat mattam |
| 12:08:05 | <Heffalump> | no, you did the other one. Can't you tell the difference between your 'm's? :-) |
| 12:08:24 | <ivanm> | ACTION 's brain hurts |
| 12:09:49 | <int-e> | @type liftM2 const |
| 12:09:51 | <lambdabot> | forall a1 a2 (m :: * -> *). (Monad m) => m a1 -> m a2 -> m a1 |
| 12:10:28 | <PantheraPardus> | err, what does mhm stand for? |
| 12:10:42 | <ivanm> | PantheraPardus: permutation of "hmm" |
| 12:11:18 | <PantheraPardus> | hmm |
| 12:12:09 | <ivanm> | ACTION resists the temptation to start that nonsense all over again |
| 12:12:47 | <PantheraPardus> | lol |
| 12:13:00 | <Heffalump> | llo |
| 12:13:12 | <ivanm> | *sigh* |
| 12:13:17 | <PantheraPardus> | ACTION waits for the last variant |
| 12:13:55 | <PantheraPardus> | let's do it ;) |
| 12:15:35 | <DRMacIver> | Hm. gtk2hs appears to have bytestring 0.9.0.5 as a dependency.This is somewhat perplexing as such a package does not exist. |
| 12:16:17 | <ivanm> | which version of gtk2hs? |
| 12:16:25 | <ivanm> | there's a bytestring-0.9.1.0 ... |
| 12:16:34 | <DRMacIver> | Yes, and I have that. |
| 12:16:44 | <DRMacIver> | gtk2hs 0.9.12.1 |
| 12:17:17 | <DRMacIver> | But the build is failing with ghc-6.8.2: unknown package: bytestring-0.9.0.5 (dependency of cairo-0.9.12.1) |
| 12:17:30 | <ivanm> | hmmm, I don't have it requring bytestring at all... |
| 12:17:50 | <ivanm> | though that's because dcoutts didn't set it as a dependenciy in the ebuild ;-) |
| 12:17:56 | <ivanm> | @seen dcoutts |
| 12:17:56 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 12:18:00 | <ivanm> | preflex: seen dcoutts |
| 12:18:01 | <preflex> | dcoutts was last seen on #gentoo-haskell 1 day, 3 hours, 31 minutes and 38 seconds ago, saying: hia ivanm |
| 12:19:19 | <DRMacIver> | There's definitely a ByteString dependency in the makefile. Even more curiously, it's set to 0.9.1.0 |
| 12:24:24 | <DRMacIver> | Hm. Couldn't be a ghc compatibility issue could it? gtk2hs only explictly mentions 6.8.1 and 6.6.1, but I'm running 6.8.2. (I can't really imagine that being the problem though) |
| 12:24:44 | <ivanm> | I doubt it |
| 12:24:55 | <ivanm> | how are you installing it? make? |
| 12:25:00 | <DRMacIver> | yeah |
| 12:25:12 | <ivanm> | ... wierd |
| 12:25:24 | <DRMacIver> | I'm really good at generating that reaction. :) |
| 12:25:56 | <ivanm> | lol |
| 12:26:37 | <DRMacIver> | Anyway, I've tried ghc-pkg hiding the old version of bytestring I also had installed and am rebuilding. Will see if that helps. |
| 12:34:14 | <DRMacIver> | That seems to have done it |
| 12:43:35 | <DRMacIver> | Is it normal to find glade completely and utterly maddening? |
| 12:43:48 | <TSC> | Yes |
| 12:43:56 | <DRMacIver> | ok. Just wanted to make sure. |
| 12:43:58 | <TSC> | At least common (: |
| 12:46:07 | <kpreid> | Disagreement: http://blog.plover.com/prog/glade.html |
| 12:46:08 | <lambdabot> | Title: The Universe of Discourse : Glade |
| 12:46:17 | <DRMacIver> | Yes, I saw that. |
| 12:46:31 | <DRMacIver> | It's a large part of why I decided to give this stuff a try. :) |
| 12:47:06 | <DRMacIver> | But it's also an example that would be trivial in any GUI builder that even pretends to the name. |
| 12:49:38 | <DRMacIver> | You never know, I might get used to it and love it. But initial impressions of the w handles widget layout and similar are very far from positive. |
| 12:51:35 | <kpreid> | DRMacIver: Ah. Yeah, I recognize the difference and was being a bit silly |
| 12:51:59 | <DRMacIver> | Fair enough. :) |
| 13:17:38 | <jaj> | I think back then when glade was able to create C/python/whatever code it was quite interesting but now that you have to depend on libglade and you have to have an xml file lying around it's a bit annoying |
| 13:18:25 | <DRMacIver> | On the other hand makes it a bit easier to use with new languages (like Haskell) :) |
| 13:18:44 | <jaj> | of course it's quite difficult to support different languages and generate good code for them |
| 13:20:15 | <jaj> | I think it would be quite interesting to create a DSL which let's you describe a GUI. I never used gtk2hs, perhaps it can do that? :) |
| 13:21:37 | <wjt> | jaj: perhaps you could write a gladexml -> Hypothetical Gtk DSL converter? :) |
| 13:22:04 | <DRMacIver> | Hm. I love it when tutorials purport to be for the version of the software you're using and refer to features that flat out don't exist. |
| 13:23:34 | <jaj> | wjt: that would be interesting :) not sure I'm up to the task but I could try |
| 13:25:37 | <DRMacIver> | And the fact that the glade documentation is full of sections like "FIXME" and "Please Write Me" continues to make me less than happy with it. :) |
| 13:53:47 | <Jaak> | deamnit, is hoogle down? |
| 13:56:05 | <ivanm> | @hoogle map |
| 13:56:06 | <lambdabot> | Prelude.map :: (a -> b) -> [a] -> [b] |
| 13:56:06 | <lambdabot> | Data.List.map :: (a -> b) -> [a] -> [b] |
| 13:56:06 | <lambdabot> | Data.ByteString.map :: (Word8 -> Word8) -> ByteString -> ByteString |
| 13:56:23 | <DRMacIver> | Jaak: Looks it |
| 13:56:58 | <jaj> | seems like haskell.org is down |
| 13:59:49 | <Jaak> | @hoogle queue |
| 13:59:49 | <lambdabot> | No matches found |
| 13:59:58 | <Jaak> | @hoogle min |
| 13:59:59 | <lambdabot> | Prelude.min :: Ord a => a -> a -> a |
| 13:59:59 | <lambdabot> | Data.Ord.min :: Ord a => a -> a -> a |
| 13:59:59 | <lambdabot> | Prelude.minBound :: Bounded a => a |
| 14:00:11 | <Jaak> | @hoogle findMin |
| 14:00:11 | <lambdabot> | Data.Set.findMin :: Set a -> a |
| 14:00:11 | <lambdabot> | Data.Map.findMin :: Map k a -> (k, a) |
| 14:00:11 | <lambdabot> | Data.IntSet.findMin :: IntSet -> Int |
| 14:04:21 | <Jaak> | and back up |
| 14:06:34 | <TomMD> | @seen areYouWorking? |
| 14:06:35 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 14:09:47 | <DRMacIver> | lambdabot is such a great example of how Haskell's strong type system helps you prevent bugs. |
| 14:09:51 | <Lycurgus> | i'd call that a bug |
| 14:10:02 | <jdh30> | lol |
| 14:10:05 | <DRMacIver> | That might have been my point... |
| 14:10:34 | <Lycurgus> | without the error message it would have been regular in-principle perfect haskell |
| 14:10:38 | <jdh30> | what are you up to these days DRMacIver? |
| 14:10:51 | <TomMD> | If only you could force files never to be corrupt using the type system. |
| 14:12:29 | <DRMacIver> | At work, visualisation software in Scala (though soon to move to ruby due to politics). At home, the usual assortment of random hackery. How about you? Still telling the world why everything except F# and OCaml are awful? |
| 14:12:52 | <jdh30> | Actually I am currently telling the world why OCaml is awful. :-) |
| 14:13:15 | <TomMD> | So that only leaves F# as acceptable? |
| 14:13:37 | <jdh30> | For me, yes. :-( |
| 14:14:01 | <TomMD> | I take it you don't have *nix as a platform often. |
| 14:14:16 | <TomMD> | *target platform |
| 14:14:32 | <jdh30> | DRMacIver: is that JRuby now or Ruby Ruby? |
| 14:15:10 | <jdh30> | Actually I am still predominantly Linux and several of our products are still Linux/OSX. I'm getting pretty sick of Linux to be honest though. |
| 14:15:38 | <Heffalump> | ACTION is very sick of Windows |
| 14:16:11 | <DRMacIver> | jdh30: JRuby. |
| 14:16:23 | <Heffalump> | .NET is quite nice though |
| 14:16:27 | <DRMacIver> | Although we do use Ruby Ruby as well, and will probably try to make most of the code portable between the two. |
| 14:16:45 | <DRMacIver> | (except for the bits that are explicitly there to use Java libraries of course) |
| 14:16:46 | <jdh30> | What is JRuby like? I get the impression it is vastly more popular that IronRuby/Python on .NET? |
| 14:17:03 | <jdh30> | Heffalump: yeah, .NET rocks. |
| 14:17:14 | <sclv> | pl ftw: any (s ==) . map (second (drop 1) . span (/= '=') . takeWhile (/= ';') ) . map snd . filter ((HeaderName "set-cookie" ==) . fst) $ hs |
| 14:17:35 | <jdh30> | I actually came here because I saw some of what DonS had written about me here. |
| 14:17:49 | <Heffalump> | what did he say? |
| 14:17:54 | <mrd> | sclv: pl? plz... (s ==) ? |
| 14:18:24 | <DRMacIver> | JRuby seems to be among the most popular of the dynamic languages for the JVM crowd. It's moving along nicely as far as I can tell. But we're way off topic for #haskell |
| 14:18:52 | <sclv> | its just a function to test if any cookie is set to a particular value on an http response. i was just happy with how condensed it came out. |
| 14:19:06 | <Heffalump> | how do types work in dynamic languages on the JVM? Is everything an object? |
| 14:19:41 | <jdh30> | he didn't understand why I alienate portions of the functional programming community, why I don't go to ICFP and so on. Here's a link: http://tuukka.iki.fi/tmp/haskell-2007-12-01.html |
| 14:19:41 | <lambdabot> | Title: haskell-2007-12-01 |
| 14:20:28 | <DRMacIver> | Heffalump: How do you mean? From a user visible point of view or from an implementation point of view? |
| 14:20:42 | <Heffalump> | DRMacIver: implementation |
| 14:20:45 | <jdh30> | DRMacIver: Yeah. I was amazed (and very happy ;-) to see this trend: http://www.google.com/trends?q=f%23%2Cironpython |
| 14:20:46 | <lambdabot> | Title: Google Trends: f#,ironpython |
| 14:21:16 | <DRMacIver> | Heffalump: I think JRuby objects implement some interface which has a method pointing to a ruby style class object. |
| 14:21:23 | <DRMacIver> | And are otherwise just objects. |
| 14:21:25 | <Heffalump> | jdh30: I vaguely remember that conversation. It seemed accurate at the time and looks that way too now from a quick skim. |
| 14:21:27 | <jdh30> | I can't explain it though. |
| 14:21:44 | <Heffalump> | jdh30: but primitive types have to be objects too? |
| 14:21:47 | <DRMacIver> | Heffalump: I'm not totally sure though. My Ruby foo is weak as hell. :) |
| 14:21:48 | <Heffalump> | sorry, not jdh30 |
| 14:21:56 | <DRMacIver> | Heffalump: Yes, they typically don't get to use primitive types |
| 14:22:09 | <Heffalump> | how does performance work out? |
| 14:22:24 | <sclv> | bad. |
| 14:22:30 | <jdh30> | I'd have thought you could optimize that away easily enough but apparently many dynamic languages make no attempt to. |
| 14:22:44 | <jdh30> | But nothing like as bad as Groovy, apparently. |
| 14:22:54 | <DRMacIver> | Heffalump: As I understand it, they tend to suffer a fair bit on numerics as a result but it's not too awful. |
| 14:23:11 | <DRMacIver> | Heffalump: They can still take advantage of arrays of primitives as far as I know. |
| 14:23:20 | <DRMacIver> | which should offset the worst of it. |
| 14:23:24 | <Heffalump> | true |
| 14:23:29 | <DRMacIver> | And I suspect a lot of primitive heavy library code is written in Java. |
| 14:24:02 | <Heffalump> | heh, writing code in java for efficiency |
| 14:24:03 | <sclv> | I don't know if its true anymore, but a big issue used to be with the jvm that object creation is expensive, compared to what one would need for a simple tagged union type or etc. |
| 14:24:21 | <jdh30> | I have actually been quite impressed with Java's performance lately. |
| 14:24:26 | <sclv> | so dynamic languages that represent everything as an object get nailed by the java runtime. |
| 14:24:29 | <Heffalump> | the .NET type system has a built-in variant style type, I wonder what implementations use it. |
| 14:24:32 | <DRMacIver> | jdh30: It's harder to do on the JVM, alas. Ruby Ruby does do some optimisations I think. |
| 14:24:44 | <jdh30> | Right. |
| 14:24:48 | <Heffalump> | I originally thought it was for VB, but it turns out that VB.NET gets rid of having that kind of thing. |
| 14:25:14 | <DRMacIver> | sclv: Allocation is pretty fast these days. The problem is more that Java objects weigh a fair bit and there's not much you can do to offset that. |
| 14:25:34 | <sclv> | java for numerics with a good jit approaches C speeds though, no? |
| 14:25:46 | <jdh30> | ish, yes. |
| 14:26:09 | <sclv> | DRMacIver: Right, but then there's also lookup for creation methods etc, too, no? |
| 14:26:24 | <Heffalump> | sclv: that's statically resolvable, though |
| 14:26:31 | <Heffalump> | constructors are the one thing that never require virtual dispatch |
| 14:26:32 | <jdh30> | I ported SciMark2 from Java to OCaml and F# recently. Java on 64-bit Debian AMD64 beats everything else except C (and even beats C on the SOR subtask where aliasing is important). |
| 14:26:38 | <sclv> | but is it statically resolved in the jvm? |
| 14:27:05 | <Heffalump> | sclv: yes |
| 14:27:05 | <DRMacIver> | jdh30: By the way, I don't think the primitives thing is something where .NET wins. |
| 14:27:25 | <sclv> | ah, good to know. |
| 14:27:41 | <DRMacIver> | jdh30: As the issue isn't just "good support for primitives" it's "providing a uniform object model over primitives and objects", which needs more low level hackery than I think either provides |
| 14:28:31 | <Heffalump> | it's not the uniform object model I was thinking of, though that may be an issue too - it's just the lack of static type information |
| 14:28:34 | <DRMacIver> | (also I suspect the issue with using objects instead of primitives is more that there are a lot of optimisations performed for primitives that aren't for their corresponding objects) |
| 14:28:41 | <jdh30> | DRMacIver: I see. I've no idea about the performance of dynamic languages on .NET, BTW. AFAICT, nobody uses them. |
| 14:28:47 | <Heffalump> | you can't represent something as an int if you don't know for sure it'll be an int |
| 14:29:10 | <jdh30> | You can certainly unbox it locally, which should be all you need for the vast majority of performance-critical sections. |
| 14:29:18 | <luite> | DRMacIver: some of the optimizations (no need for garbage collection etc) can now be performed in specific cases for objects too, because jvm 1.6 has escape analysis |
| 14:29:40 | <DRMacIver> | luite: I was thinking more in terms of numerics, loop optimisations, etc. |
| 14:30:24 | <Heffalump> | luite: as in the JIT in Sun JVM 1.6 does the analysis? Or do you mean that there is something added to the JVM spec to make it easier? |
| 14:31:01 | <DRMacIver> | Heffalump: I think the sun 1.6 JVM has the capability to do escape analysis but it's switched off |
| 14:32:21 | <luite> | I read some articles about it, but I'm not sure whether it is actually already used. 1.6 does have some performance improvements, but that might be because of some other optimizations (register allocation) |
| 14:34:28 | <DRMacIver> | Heffalump: The uniform object model and lack of static type checking are both part of the same issue here though. If you can treat an Int as an object, you need to box it a lot of the time. If you *always* treat an int as an object (because of the dynamic typing) then you have to box it all the time. |
| 14:34:50 | <DRMacIver> | Scala suffers from the first problem and its a noticable performance hit far more often than I'd like |
| 14:35:01 | <DRMacIver> | (though not as bad as for the dynamic languages) |
| 14:35:13 | <Heffalump> | can't you just box it when it's used as an object? |
| 14:35:33 | <Heffalump> | or do the mutability semantics force that to happen when it's passed to things as well? |
| 14:35:57 | <DRMacIver> | Yes, and Scala does for the most part. But there are a lot of cases where it does have to be treated as an object. |
| 14:36:20 | <DRMacIver> | For example you have to box an int to pass it through the identity function. |
| 14:36:38 | <DRMacIver> | Parameterized things don't get templated for primitives, so basically every time you hit a type parameter you have to box |
| 14:37:17 | <Heffalump> | ah, yes |
| 14:37:20 | <Baughn> | That's scala. GHC does specialize them, right? |
| 14:37:31 | <Heffalump> | Baughn: typically only by inlining |
| 14:37:47 | <Heffalump> | I think it only specializes if you tell it to (with a pragma) though I could be wrong |
| 14:38:45 | <Baughn> | Heffalump: Mm. That's one optimization I could see helping - there usually aren't enough types passing through a polymorphic function that boxing is better than specializing, I don't think. There aren't too many that can be unboxed in the first place. |
| 14:39:10 | <DRMacIver> | Generally speaking comparing Scala optimisations with GHC ones makes the Scala compiler team sad. :) |
| 14:39:21 | <Heffalump> | Baughn: well, it's a code bloat issue |
| 14:39:25 | <Baughn> | But if it already has the machinery, and just doesn't do it by default, that suggests I'd be wrong |
| 14:39:28 | <Heffalump> | DRMacIver: is scala strict or lazy? |
| 14:39:52 | <DRMacIver> | Strict with optional laziness. |
| 14:40:03 | <Baughn> | Heffalump: I suppose. There /is/ something to be said for haskell programs fitting in L2 cache |
| 14:40:07 | <DRMacIver> | Although I have some Issues with the laziness implementation. I keep meaning to see if I can improve it. |
| 14:40:12 | <Heffalump> | Baughn: if you're talking about GHC, then you can't pass unboxed stuff to polymorphic things anyway |
| 14:40:30 | <Heffalump> | as an optimisation, you could specialise the thing and unbox the parameter together |
| 14:40:34 | <DRMacIver> | (It plays very badly with the garbage collector) |
| 14:40:35 | <Baughn> | Heffalump: Well, not /explicitly/ unboxed stuff |
| 14:40:42 | <Heffalump> | right |
| 14:40:55 | <Heffalump> | but since you have to do both together, it's probably rather harder to decide to do so |
| 14:42:20 | <Baughn> | DRMacIver: If you do look at that, I'd love to have time-driven weak references. That is to say, weak references that get collected in LRU order |
| 14:42:42 | <DRMacIver> | Sorry, I meant the Scala laziness implementation. :) I wouldn't know where to start with GHC's |
| 14:43:10 | <EvilTerran> | Baughn, ooh, that's terribly clever |
| 14:43:20 | <DRMacIver> | And Scala isn't pure, so that's not really appropriate for its laziness. |
| 14:43:26 | <pejo> | Isn't the implementation in GHC pretty good, considering how well it does in the shootout? |
| 14:43:30 | <jdh30> | Does Scala get JIT-time type specialized like F#? |
| 14:43:37 | <Baughn> | pejo: Sure, but it can always get better |
| 14:43:46 | <DRMacIver> | (But yes, I've often wondered about something like that as well) |
| 14:43:55 | <EvilTerran> | so, if some big expression gets CSEd and unexpectedly cached for a long time, and it's being held in a weak reference, it can be GCed and re-calculated if there's not enough memory to keep it around |
| 14:44:00 | <DRMacIver> | jdh30: No more so than anything on the JVM does. |
| 14:44:16 | <Baughn> | EvilTerran: Yep, that's the idea |
| 14:44:31 | <Heffalump> | but then the GC would need to roll the expression back to the uncomputed state, too |
| 14:44:40 | <EvilTerran> | i love it. seems like a great solution to the CSE-isn't-always-an-optimisation problem |
| 14:44:55 | <Heffalump> | and that might well take up more space anyway.. |
| 14:45:10 | <EvilTerran> | altho Heffalump has a point - a weak reference would have to include a reference to the unevaluated thunk |
| 14:45:10 | <Baughn> | Heffalump: True. It wouldn't always be a win, so you'd want to do it explicitly |
| 14:45:30 | <Heffalump> | also, LRU doesn't make too much sense on its own, you need to trace the LRUness right through |
| 14:45:33 | <Baughn> | EvilTerran: We'd have to play tricks with the local page table, though. I'm not sure how it'd work on platforms that don't /have/ a user-level page table, ie. non-x86 |
| 14:46:04 | <Baughn> | Hm |
| 14:46:35 | <EvilTerran> | aaaand suddenly the conversation's over my head. never mind, IANA compiler designer :P |
| 14:46:37 | <Baughn> | Keep a counter of weak-thunks-evaluated, increment and assign every time you dethunk one, store in sorted order? |
| 14:47:00 | <Baughn> | Or don't keep a counter, and just use the memory location for same |
| 14:47:01 | <Heffalump> | re the page table, you want to keep all the weak stuff in separate pages that you can just drop? |
| 14:47:29 | <Baughn> | Yes, and so you can track LRUness by reading the access bit on said table |
| 14:47:46 | <Baughn> | x86 tracks accesses to pages, both reads and writes. It's very handy |
| 14:48:14 | <Baughn> | The granularity could be an issue, though.. *ponder* |
| 14:48:18 | <Heffalump> | yeah |
| 14:48:35 | <Heffalump> | have you read the PLDI '05 paper on this subject (using page tables with GC)? |
| 14:49:03 | <Baughn> | No. I'm sure it'd be interesting, but I'm not normally on the internals side of things |
| 14:49:21 | <Baughn> | (And I have a few hundred papers scheduled to read already. :P) |
| 14:49:47 | <EvilTerran> | ACTION notes that it'd be occasionally handy to have (^-) x y = x ^^ (-y) |
| 14:49:57 | <jdh30> | Are there any industrial programmers here? |
| 14:50:05 | <EvilTerran> | so you could write stuff like (2^-10) |
| 14:50:15 | <Heffalump> | how do you define industrial? |
| 14:50:52 | <jdh30> | Make products and sell them to make money. |
| 14:51:02 | <jdh30> | So MSR doesn't count. |
| 14:51:10 | <Heffalump> | even F#? |
| 14:51:32 | <jdh30> | Not when it was in MSR, no. |
| 14:51:42 | <Heffalump> | ok, so Don Syme doesn't count? |
| 14:51:50 | <jdh30> | Don is productizing it. |
| 14:52:01 | <Heffalump> | he's still in MSR |
| 14:52:21 | <jdh30> | He's in Redmond. |
| 14:52:47 | <Heffalump> | that doesn't preclude him being in MSR.. |
| 14:52:58 | <Heffalump> | but fair enough if he's temporarily moved to a product group again |
| 14:53:13 | <jdh30> | He is in Redmond working on F# with the product team. Yes. |
| 14:53:22 | <DRMacIver> | Do you consider services companies and/or people developing internal tools to be "industrial"? |
| 14:53:29 | <Baughn> | So.. weak reference = (reference/thunk, thunk copy, last access time). Keep a global counter for accesses; update the access time anytime you actually dereference it explicitly. In times of memory pressure (must be tunable) allow the GC to collect the /least recently/ accessed reference, copying back the thunk. Problem: If you hang on to references to inside whatever structure your weak ref is holding, you could conceivably get multiple |
| 14:53:37 | <Heffalump> | anyway, can you prove MS are going to make money from F#? |
| 14:53:46 | <DRMacIver> | (Neither of which apply to me. I fit into that category fairly unambiguously) |
| 14:53:51 | <jdh30> | Yes but they are uninteresting if their work is invisible from the outside. |
| 14:53:52 | <Heffalump> | given that they probably won't change the price of VS anyway |
| 14:53:57 | <DRMacIver> | (though not using Haskell, alas) |
| 14:53:59 | <jdh30> | MS already have made money from F#. |
| 14:54:05 | <Heffalump> | oh, how? |
| 14:54:16 | <Heffalump> | people write about internal work they do externally, sometimes |
| 14:54:43 | <DRMacIver> | Baughn: You cut off at "conceivably get multiple c" |
| 14:55:50 | <Baughn> | DRMacIver: The thunk can end up being evaluated multiple times, producing multiple, identical data structures that are all held in memory by non-weak references |
| 14:55:57 | <Baughn> | DRMacIver: The programmer would have to be careful |
| 14:55:58 | <jdh30> | Yes. The occasional writings can make these things visible from the outside but it is much less interesting that a real product. For example, it would be much more interesting to be able to quantify revenue objectively rather than have someone conjecture as to their work's internal worth. |
| 14:56:27 | <Heffalump> | jdh30: sure. But the same thing applies to a product that is bundled up with a much bigger thing, like F#. |
| 14:56:37 | <Twinside> | hello everyone |
| 14:56:41 | <jdh30> | Heffalump: MS are already making money from F# because people are migrating to .NET because of it and, inevitably, buying VS and other developer tools. |
| 14:56:53 | <Heffalump> | and you can quantify that? |
| 14:57:01 | <jdh30> | Quantify what? |
| 14:57:08 | <Heffalump> | what money they have made from F# |
| 14:57:37 | <jdh30> | You could make a pretty good estimate for now but they will start making serious money when 1.0 is out later this year. |
| 14:57:46 | <pejo> | jdh30, isn't VS a necessary evil that doesn't generate any direct revenue for MS? |
| 14:58:04 | <Baughn> | All things aren't quantifiable. How much money has Foo Company made because their programmers are better as a result of learning haskell, despite their not actually /using/ haskell? |
| 14:58:07 | <jdh30> | VS generates some revenue but nothing like as much as Office, of course. |
| 14:58:27 | <jdh30> | Some things are quantifiable, of course. |
| 14:58:31 | <Heffalump> | jdh30: go on then (make a "pretty good estimate") |
| 14:58:38 | <[Justice]> | it could be argued that Microsoft's core business is VS |
| 14:58:49 | <jdh30> | Justice: yes. |
| 14:58:50 | <Heffalump> | [Justice]: it could be argued, but it'd be wrong :-) |
| 14:58:58 | <Twinside> | I've got an error of "rigid type" with ghc, but I've got issues to really understand what the problem is, can someone help me? |
| 14:58:59 | <sclv> | F# is probably keeping some companies from jumping ship away from .NET, actually. |
| 14:59:17 | <Baughn> | Twinside: Sure, if you post the entire error message and preferably code |
| 14:59:17 | <jdh30> | Not really, Microsoft depend upon third party developers building the applications that their end users buy. That is the foundation of their entire platform. |
| 14:59:23 | <Heffalump> | you'd have to make a very indirect argument about VS helping to maintain the dominance of the Windows platform |
| 14:59:28 | <Lycurgus> | really (re F#)? |
| 14:59:31 | <Twinside> | Baughn > in channel or in private? |
| 14:59:38 | <Baughn> | Twinside: In pastebin |
| 14:59:41 | <Heffalump> | Twinside: http://hpaste.org |
| 14:59:50 | <jdh30> | Lycurgus: definitely. |
| 15:00:07 | <Heffalump> | jdh30: got examples? |
| 15:00:10 | <[Justice]> | not necessarily VS the product, VS the idea of developers writing programs for Windows |
| 15:00:24 | <Lycurgus> | my impression is that only a miniscule number of .net shops ever heard of F# |
| 15:00:34 | <Lycurgus> | or haskell for that matter |
| 15:00:37 | <[Justice]> | .net shops aren't going to write in F# |
| 15:00:40 | <[Justice]> | or haskell |
| 15:00:49 | <jdh30> | Lycurgus: that is precisely why it is good: F# will attract people from other platforms (like me) rather than simply stealing from C#. |
| 15:00:53 | <sclv> | Lycurgus: I know some banks that are moving to increasingly functional methods, and are using F# to work with extant systems. |
| 15:00:55 | <[Justice]> | .net shops are going to stick with VB7 |
| 15:01:02 | <EvilTerran> | [Justice], ah, you mean "get everyone writing in .net so they'll get vendor lock-in and be stuck on windows"? |
| 15:01:43 | <hpaste> | Twinside pasted "Compilation problem" at http://hpaste.org/8018 |
| 15:01:46 | <pejo> | I think we got slightly sidetracked from Haskell all the sudden. Perhaps this conversation should move to #haskell-blah? |
| 15:01:52 | <[Justice]> | exactly, banks & financial institutions, researchers, etc need F# or functional languages in general |
| 15:02:01 | <Lycurgus> | i was surprised to find out how mono works |
| 15:02:02 | <Twinside> | Baughn > done |
| 15:02:06 | <jdh30> | EvilTerran: Even if it is possible for people to migrate to Mono they won't because it will remain so much worse. |
| 15:02:12 | <DRMacIver> | The only .NET shop I've worked in (well, it was about half .NET shop half Java shop, but it startd as a .NET shop) used C#. I expect a couple people there had heard of F# but there wouldn't have been a snowball's chance in hell of using it. |
| 15:02:14 | <EvilTerran> | Lycurgus, in what way? |
| 15:02:22 | <Heffalump> | pejo: I would argue that language discussions belong here unless they are blatantly not at all to do with Haskell |
| 15:02:28 | <Lycurgus> | it uses the .net binaries |
| 15:02:33 | <EvilTerran> | oh, right |
| 15:02:59 | <sclv> | My understanding is that msoft is very friendly towards the Mono ppl actually. |
| 15:03:06 | <[Justice]> | MS building a superb platform for developing software is ... a problem? |
| 15:03:08 | <EvilTerran> | Lycurgus, ... as in the windows runtimes that MS wrote? |
| 15:03:11 | <Lycurgus> | so it doesn't hit that recreate the world situation |
| 15:03:15 | <sclv> | although it might go all evil-empire on them later, of course. |
| 15:03:21 | <Lycurgus> | ET: yes. |
| 15:03:25 | <EvilTerran> | cunning |
| 15:03:26 | <EvilTerran> | i like that |
| 15:03:31 | <Heffalump> | [Justice]: well, it could be, in the same way as them bundling IE with Windows was a problem |
| 15:04:06 | <jdh30> | DRMacIver: Yes, existing .NET shops are not likely to use F#. Other people will. |
| 15:04:11 | <Heffalump> | ACTION is still waiting for jdh30's F# revenue estimates and examples of it stopping people moving away from .NET :-) |
| 15:04:35 | <jdh30> | sclv: Consider what it would take to threaten Microsoft now and look at how fast Mono is progressing. I can't see the curves ever meeting. |
| 15:04:38 | <[Justice]> | F# is keeping me hoping for an H# ... there's one example |
| 15:04:44 | <Heffalump> | Baughn: are you looking at Twinside's error? Otherwise I will, I just don't want to duplicate work as those things usually take some work to understand. |
| 15:05:07 | <DRMacIver> | Heffalump: It's such an easy estimate to do that it's been left as an exercise for the reader? :) |
| 15:05:14 | <Baughn> | Heffalump: I'm looking, but I think you'd better do it. THis is into trial-error-and-read territory for me |
| 15:05:17 | <jdh30> | I would guess $1M just from people toying with F# for now. I'd expect that to rise to $100M over the next few years, as it sees more serious adoption. |
| 15:05:36 | <DRMacIver> | ACTION holds up his "citation needed" banner |
| 15:05:39 | <Heffalump> | jdh30: that sounds like a conjecture, not an objective quantification |
| 15:05:50 | <EvilTerran> | [Justice], isn't there a Haskell.net project hiding somewhere already? |
| 15:06:02 | <[Justice]> | *shrug* |
| 15:06:05 | <jdh30> | Just multiply the cost of VS by the number of relevant F# users. |
| 15:06:10 | <Lycurgus> | 'conjecture' is kind |
| 15:06:11 | <sjanssen> | isn't F# free? |
| 15:06:21 | <sclv> | sjanssen: but VS is not. |
| 15:06:22 | <[Justice]> | there's an abandoned alpha VS plugin for Haskell |
| 15:06:24 | <EvilTerran> | if not, it'd be a good use of YHC's pluggable backends |
| 15:06:28 | <jdh30> | F# is free but you need commercial tools to make it useful. |
| 15:06:33 | <Twinside> | is my error resulting of a bad design? |
| 15:06:36 | <jdh30> | VS is also free (you can use F# with the free VS shell). |
| 15:06:47 | <Heffalump> | jdh30: (a) how do you know how many "relevant F# users" there are and (b) how do you know they wouldn't have bought VS anyway, or just use it from the shell? |
| 15:06:52 | <Heffalump> | and what commercial tools do you need? |
| 15:06:59 | <jdh30> | The money comes from things like VS team edition for its profiler. You can't write performant code without a profiler and most F# users will want to. |
| 15:07:31 | <Heffalump> | but those tools are free if you already have VS for other reasons |
| 15:07:44 | <jdh30> | The relevant F# users are among our customers, so that is easy. We also do market research among prospective customers and non-MS users account for almost half. |
| 15:07:50 | <jdh30> | Yes, they are the other half. |
| 15:07:54 | <conal> | what's the ghc flag for showing which rewrite rules fire |
| 15:07:56 | <vixey> | someone took the book out the library I wanted |
| 15:08:00 | <vixey> | I bet it was someone here! |
| 15:08:15 | <Heffalump> | vixey: what library? :-) |
| 15:08:22 | <vixey> | conal: -v I think .. notsure |
| 15:08:37 | <EvilTerran> | ACTION seems to be in the right country to have taken it, at least |
| 15:08:44 | <jdh30> | Has anyone tried H |
| 15:08:51 | <jdh30> | H#, the Haskell for .NET? |
| 15:08:52 | <DRMacIver> | When you say "our", I can't help but notice that the other members of your company are conspicuously silent... |
| 15:08:55 | <conal> | vixey: i'll try that. thx. |
| 15:08:58 | <Heffalump> | Twinside: ok, so the problem is that you haven't made your serialize polymorphic enough |
| 15:09:12 | <jdh30> | Yes. I am the vocal member. :-) |
| 15:09:21 | <Twinside> | Heffalump > how's that? |
| 15:09:22 | <Heffalump> | your type signature says that if you are implementing StrictPixel for a certain b, you have to make serialize work for *any* b |
| 15:09:22 | <EvilTerran> | vixey, what book, anyway? |
| 15:09:43 | <Heffalump> | sorry, "implementing it for a certain 'a'" |
| 15:09:45 | <DRMacIver> | It's not so much "vocal" as "not completely mute and invisible" in this case. |
| 15:09:48 | <Heffalump> | but you have made b = a |
| 15:10:00 | <jdh30> | Yes. |
| 15:10:08 | <sjanssen> | conal: -ddump-simpl-stats |
| 15:10:11 | <conal> | ah, found it: -ddump-rules |
| 15:10:14 | <conal> | sjanssen: thx! |
| 15:10:16 | <vixey> | EvilTerran; did you get any books out by Luo Zhaohui? :p |
| 15:10:24 | <EvilTerran> | er... no. |
| 15:10:25 | <vixey> | (like yesterday) |
| 15:10:26 | <Twinside> | Heffalump > the compiler can't unify this? because a = b is a possible case for me |
| 15:10:48 | <Heffalump> | Twinside: it's a possible case, but your signature says it must work for *all* cases |
| 15:10:52 | <jdh30> | She is actually quite visible though, albeit only IRL. |
| 15:10:57 | <sclv> | you need mptcs and fundeps, maybe? |
| 15:11:09 | <EvilTerran> | vixey, not out of any oxford library, and definitely not out of a library anywhere else |
| 15:11:09 | <Heffalump> | either make 'b' be another parameter to the class, or fix the class so that b is always a |
| 15:11:41 | <vixey> | ACTION has to wait ages until to get it :/ |
| 15:11:59 | <Twinside> | Heffalump > ok I'm going to try adding another parameter to the class, thanks |
| 15:12:26 | <Heffalump> | jdh30: H# doesn't really seem to have much sign of life |
| 15:12:51 | <jdh30> | That is the impression I got. OCamlJava is showing signs of life but it has lots of problems, unfortunately. |
| 15:12:58 | <[Justice]> | H# isn't a real thing, so far as i know ... i meant, a Haskell on the CLR |
| 15:13:04 | <jdh30> | I'm surprised they didn't target Mono instead... |
| 15:13:05 | <Heffalump> | re "relevant F# users", who are they? |
| 15:13:12 | <jdh30> | Oh. |
| 15:13:24 | <jdh30> | Relevant F# users are the ones who did not already own .NET dev tools. |
| 15:13:28 | <DRMacIver> | Haskell seems really unsuited for running on existing virtual machines. |
| 15:13:39 | <Heffalump> | no, I mean give names. Otherwise we just have your unverified assertions. |
| 15:13:45 | <[Justice]> | so did ruby and python |
| 15:13:47 | <DRMacIver> | Is that just a misunderstanding on my part? |
| 15:13:48 | <Twinside> | Heffalump > thanks it work very well :) |
| 15:13:54 | <jdh30> | Depending what Haskell users require, that might not be a practically-important concern |
| 15:14:31 | <DRMacIver> | [Justice]: Not really. |
| 15:14:32 | <Heffalump> | .NET would be nice to have, cos of all the infrastructure that already exists |
| 15:14:32 | <jdh30> | I cannot name my customers, of course. |
| 15:14:35 | <DRMacIver> | [Justice]: Ruby and python execution both fall into the same class of problems as smalltalk, and the JVM at least owes a lot to smalltalk VMs. |
| 15:14:45 | <Heffalump> | and because it's stupid for to be implementing libraries once per platform |
| 15:15:07 | <DRMacIver> | And the bits where it doesn't match up terribly well with the smalltalk VMs are exactly where the implementations on the JVM have all the predicted problems. :) |
| 15:15:37 | <Heffalump> | jdh30: so your claims about revenue to Microsoft are completely unverifiable. It's not even as if you *are* Microsoft, you're just some random consultant who likes evangelizing F#. |
| 15:15:48 | <jdh30> | Heffalump: absolutely. You don't need .NET though: the creators of Linux-based FPLs could just collaborate on a suitable VM design. Well, that is the theory. In practice, they have never managed to collaborate on anything for long enough to see it through to completion and none of them have ever managed to write a working concurrent GC. |
| 15:16:02 | <DRMacIver> | Good compilation of Haskell on the other hand seems to rely on a lot of control over the stack (which I think is why ghc doesn't even use the x86 stack?) and heap (e.g. doing a lot of on heap replacement) |
| 15:16:18 | <Heffalump> | DRMacIver: GHC does a lot of on heap replacement? |
| 15:16:22 | <DRMacIver> | I thought it did |
| 15:16:26 | <DRMacIver> | I may be completely wrong! |
| 15:16:32 | <Heffalump> | I didn't, but I could be wrong too :-) |
| 15:17:04 | <jdh30> | Heffalump: You can easily verify it by counting them yourself. Just post on a relevant forum and I am sure you will get a lot of responses. |
| 15:17:11 | <DRMacIver> | I may also be using the wrong terms. Brief possibilities at ARM aside I'm very much not a compiler engineer. :) |
| 15:17:29 | <jdh30> | I met someone from ARM in my antenatal classes. |
| 15:17:32 | <Heffalump> | "in-place update" is the term I'd use, but it's clear what you meant |
| 15:17:43 | <Heffalump> | they're everywhere.. |
| 15:17:45 | <DRMacIver> | but e.g. I was under the impression that when you evaluated a thunk it replaced the original with the result |
| 15:17:58 | <jdh30> | I suppose if I said "our antenatal classes" someone would accuse me of cloning because my wife is "invisible". ;-) |
| 15:18:02 | <Heffalump> | DRMacIver: well, it'll overwrite the pointer with the value, yes. But that's not really a big deal. |
| 15:18:16 | <Heffalump> | jdh30: does your wife actually write F#? |
| 15:18:22 | <jdh30> | No. |
| 15:18:23 | <[Justice]> | *shrug* i dunno what ghc does ... but i guess you could check out the C source it emits |
| 15:18:34 | <Heffalump> | what does she do, then? |
| 15:18:38 | <DRMacIver> | Heffalump: It is if you have multiple copies of it floating around isn't it? |
| 15:18:42 | <jdh30> | Publishing and marketing. |
| 15:18:45 | <Baughn> | [Justice]: I would not recommend that. Read the documentation instead.. really |
| 15:18:49 | <jdh30> | Graphic design. |
| 15:18:52 | <jdh30> | etc. |
| 15:19:09 | <Heffalump> | so you're the only engineer? |
| 15:19:10 | <[Justice]> | > man ghc |
| 15:19:11 | <lambdabot> | Not in scope: `ghc' |
| 15:19:14 | <jdh30> | Oh, and she is a veterinary surgeon. :-) |
| 15:19:17 | <jdh30> | Yes. |
| 15:19:28 | <[Justice]> | lambdabot says the docs are missing |
| 15:19:36 | <Heffalump> | this is why you saying "our" when talking about technical things tends to sound ridiculous |
| 15:19:52 | <vixey> | [Justice]: get them from HTTP |
| 15:20:12 | <Baughn> | [Justice]: http://hackage.haskell.org/trac/ghc/wiki/Commentary |
| 15:20:13 | <lambdabot> | Title: Commentary - GHC - Trac |
| 15:20:35 | <jdh30> | Using the plural is perfectly normal in both academia and industry. |
| 15:20:41 | <DRMacIver> | Heffalump: e.g. if you alias a thunk a lot of times and then evaluate it you need to either update all those aliases, update the current heap location in place, or add an additional level of indirection to make it work. |
| 15:20:59 | <Heffalump> | DRMacIver: yeah, ok |
| 15:21:03 | <DRMacIver> | Heffalump: And the third is really the only one you can do on the JVM or .NET because there's no way to replace the object on the heap. |
| 15:21:16 | <Heffalump> | oh, right. Good point. |
| 15:21:36 | <Heffalump> | I was thinking of "proper" in-place update where you actually skip the GC step when an object becomes dead and can be reused. |
| 15:21:37 | <jdh30> | Incidentally, that was a large part of what I was saying before: my perspective is one of an industrial user and not one of a functional programming evangelist. |
| 15:21:43 | <DRMacIver> | I'm not saying this is a big deal if you control the low level implementation. |
| 15:21:54 | <DRMacIver> | I'm saying that things like this are why it's not easy if you *don't* have that control. |
| 15:22:07 | <Heffalump> | jdh30: an industrial user as in you sell products for money (your own definition from above)? |
| 15:22:18 | <jdh30> | Exactly, yes. |
| 15:22:18 | <Heffalump> | DRMacIver: yeah, fair enough |
| 15:22:30 | <DRMacIver> | phew. Glad I'm not totally on the wrong track. :) |
| 15:23:06 | <Heffalump> | I think the weird control-flow that GHC compiles to is the biggest obstacle, though |
| 15:23:35 | <DRMacIver> | in what sense? |
| 15:24:05 | <Heffalump> | it makes verification hard |
| 15:24:12 | <DRMacIver> | Ah |
| 15:24:25 | <Heffalump> | current verification is very much based on traditional stack-based structured code |
| 15:24:26 | <[Justice]> | sure |
| 15:24:46 | <[Justice]> | and at some point, MS will give us support for lazy evaluations |
| 15:24:46 | <Heffalump> | (even though bytecode isn't actually structured, functions are well-defined etc) |
| 15:24:58 | <Heffalump> | [Justice]: on .NET? I find that very unlikely. |
| 15:25:10 | <DRMacIver> | Why unlikely? |
| 15:25:12 | <Heffalump> | They won't even add higher-kinded type variables to .NET to make F#'s monads properly abstractable. |
| 15:25:24 | <DRMacIver> | Politically or technically? |
| 15:25:27 | <DRMacIver> | Ah |
| 15:25:50 | <Heffalump> | I dunno which you'd describe it as, but essentially the core design of .NET is "done", AIUI. |
| 15:25:57 | <jdh30> | AFAIK they have completely stopped developing .NET now. |
| 15:26:13 | <vixey> | why people are concerned with .net I will never know.. |
| 15:26:28 | <DRMacIver> | That's encouraging. Maybe the JVM will have time to catch up. :) |
| 15:26:33 | <jdh30> | .NET accounts for most of our revenue. That's why we care about it. |
| 15:26:35 | <Heffalump> | vixey: because it's very convenient, particularly if you care about binary distribution |
| 15:26:53 | <Heffalump> | which is why it has so much more traction in the commercial world than in the open-source world |
| 15:28:00 | <jdh30> | DRMacIver: apparently Sun are still working on tail calls. <yawn> |
| 15:28:05 | <[Justice]> | it's so easy to write in .net |
| 15:28:19 | <jdh30> | and its so easy to sell with .NET. |
| 15:28:21 | <vixey> | jdh30: why "<yawn>"? |
| 15:28:33 | <[Justice]> | because .net has had tail calls since 1.0 |
| 15:28:55 | <[Justice]> | not C# or VB, but it's in the CLR |
| 15:28:57 | <jdh30> | They've been talking about tail calls for several years now but have yet to actually implement anything at all. |
| 15:29:21 | <sclv> | preflex: seen ndm |
| 15:29:21 | <preflex> | ndm was last seen on #haskell 2 days, 4 hours, 4 minutes and 33 seconds ago, saying: mm_freak_work: its a lot of work to learn! just trying to help before people search the Prelude, which gets very confusing |
| 15:29:24 | <DRMacIver> | With the da vinci VM they're starting to do a lot more experimentation with adding new features. |
| 15:29:54 | <jdh30> | As soon as Sun add tail calls to the JVM there will be a huge flurry of ported and new FPLs built upon the JVM and we shall certainly diversify to them. In the mean time, we're F# only for software products. |
| 15:30:03 | <Heffalump> | jdh30: so how much money do you make selling F# products? |
| 15:30:24 | <jdh30> | ~$100k p.a. |
| 15:30:41 | <jdh30> | Sorry, halve that (the other half is services). |
| 15:31:20 | <DRMacIver> | There seems to be some work on first class continuations (I suspect that won't ever make it into the real thing, but who knows), Java 1.7 is purported to have tail calls planned although I've not seen an official comment to that effect and a bunch of other interesting features. |
| 15:31:21 | <Heffalump> | ah, I was about to say that's quite impressive |
| 15:31:24 | <vixey> | jdh30: why do you think that? If someone wanted to target the jvm it shouldn't think it makes much difference (implementing TCO in the compiler itsself is relatively simple) |
| 15:31:35 | <DRMacIver> | vixey: No, it's really not. :( |
| 15:31:40 | <DRMacIver> | Not on the JVM anyway |
| 15:31:41 | <Heffalump> | I'll be more impressed once you can make more from writing F# than I do from writing Haskell :-) |
| 15:31:45 | <clkao> | hi! are there cli tools that i can read installed module docs withoug going to hoogle ? |
| 15:31:54 | <jdh30> | OCaml for Scientists was making a similar amount but it has since all but died. Fortunately the F#.NET Journal rose at exactly the same time. |
| 15:32:03 | <Baughn> | DRMacIver: Call me when it gets first-class functions |
| 15:32:16 | <opqdonut> | clkao: haddock |
| 15:32:28 | <jdh30> | vixey: Like David said, it really isn't easy at all. Even if you manage to implement the workaround the results are awful (obfuscated call stacks and terrible performance). |
| 15:32:54 | <jdh30> | TCO is absolutely critical for a wide variety of idiomatic code. So the lack of proper tail calls on the JVM is really holding it back as far as FPL implementations are concerned. |
| 15:32:56 | <DRMacIver> | Baughn: First class functions aren't really a VM detail. The object support works quite happily for them for the most part. But it's getting method handles and lightweight classloading of anonymous classes. |
| 15:32:58 | <mtag55> | hi |
| 15:33:03 | <DRMacIver> | Or at least they're planned. Whether it gets them is unknown. |
| 15:33:18 | <mtag55> | i have a function with a parameter a |
| 15:33:20 | <Baughn> | DRMacIver: Oh, I meant java 1.7, not the jvm |
| 15:33:31 | <DRMacIver> | Oh, I don't give a shit about Java 1.7 :) |
| 15:33:38 | <vixey> | jdh: shouldn't cause performance problems, but yeah you wouldn't get nice backtraces |
| 15:33:41 | <mtag55> | when i run the program it say type error in application |
| 15:33:46 | <mtag55> | term a |
| 15:33:51 | <DRMacIver> | ACTION hasn't written more than a few hundred lines of Java in the last few months. |
| 15:33:52 | <mtag55> | type : integer |
| 15:33:57 | <Heffalump> | vixey: don't you have to make huge methods to work around lack of tailcalls? |
| 15:33:58 | <mtag55> | does not match : int |
| 15:33:59 | <jdh30> | vixey: the workaround relies upon exception handling which is really slow on the JVM. |
| 15:34:04 | <mtag55> | what can i do? |
| 15:34:05 | <Heffalump> | and how do you tailcall to something that isn't statically known? |
| 15:34:06 | <DRMacIver> | I'm purely interested in the VM and libraries at this point. |
| 15:34:11 | <DRMacIver> | jdh30: No, it's not. |
| 15:34:19 | <DRMacIver> | jdh30: It's consistently better than exception handling on .NET |
| 15:34:26 | <DRMacIver> | What's slow is stack trace generation. |
| 15:34:29 | <DRMacIver> | Which is easy to turn off |
| 15:34:32 | <jdh30> | But 10-30x slower than OCaml. |
| 15:34:41 | <vixey> | Heffalump: no, you can pass continuations around (a continuation could be as simple as a single integer) |
| 15:35:03 | <Heffalump> | vixey: oh, I see. Fair enough. |
| 15:35:11 | <mtag55> | a actually use term "a" also like list !! a and like (a + 1) |
| 15:35:14 | <DRMacIver> | jdh30: I really doubt it. You're almost certainly comparing with stack trace exceptions to ocaml exceptions. |
| 15:35:19 | <mtag55> | how must i declare the type of a? |
| 15:35:27 | <DRMacIver> | Without the stack introspection most of the time hotspot turns exception throwing into gotos. |
| 15:35:45 | <mtag55> | can anybody help? |
| 15:36:04 | <jdh30> | Only local exceptions and stack unwinding exceptions from trampolining are anything but local. |
| 15:36:06 | <vixey> | mtag55: I don't understand what you're asking |
| 15:36:10 | <Heffalump> | mtag55: hpaste your code |
| 15:36:14 | <Heffalump> | or at least the error |
| 15:36:22 | <mtag55> | - Type error in application |
| 15:36:22 | <mtag55> | *** Expression : costuri !! a |
| 15:36:22 | <mtag55> | *** Term : a |
| 15:36:22 | <mtag55> | *** Type : Integer |
| 15:36:22 | <mtag55> | *** Does not match : Int |
| 15:36:33 | <vixey> | ohh |
| 15:36:42 | <Heffalump> | for next time, hpaste = http://hpaste.org, not do it on channel |
| 15:36:50 | <mtag55> | ok |
| 15:36:51 | <vixey> | :t fromIntegral :: Integer -> Int |
| 15:36:52 | <lambdabot> | Integer -> Int |
| 15:36:57 | <vixey> | so one thing you could do is write |
| 15:37:04 | <Heffalump> | mtag55: where did a come from? |
| 15:37:04 | <vixey> | costuri !! (fromIntegral a) |
| 15:37:12 | <vixey> | but I think it might be better to redefine !! |
| 15:37:22 | <mtag55> | how? |
| 15:37:26 | <Heffalump> | I think it would be better to figure out why a needs to be an Integer and stop it being one, if possible! |
| 15:37:40 | <Heffalump> | if it really needs to be one, then using it for !! would have some issues... |
| 15:37:46 | <vixey> | (x:_)!!0=x;(_:xs)!!(n+1)=xs!!n |
| 15:38:00 | <EvilTerran> | ?hoogle [a] -> Integer -> a |
| 15:38:01 | <lambdabot> | No matches, try a more general search |
| 15:38:15 | <vixey> | :t let (x:_)!!0=x;(_:xs)!!(n+1)=xs!!n in (!!) |
| 15:38:15 | <Heffalump> | @type Data.List.genericIndex |
| 15:38:17 | <Deewiant> | vixey: how about (!!) = genericIndex |
| 15:38:17 | <lambdabot> | forall t t1. (Integral t1) => [t] -> t1 -> t |
| 15:38:18 | <lambdabot> | forall b a. (Integral a) => [b] -> a -> b |
| 15:38:18 | <EvilTerran> | Data.List.genericIndex :: Integral a => [b] -> a -> b |
| 15:38:30 | <EvilTerran> | that's the one i was thinking of |
| 15:40:03 | <DRMacIver> | jdh30: As far as I know, it's pretty good about non local exceptions too |
| 15:40:24 | <jdh30> | DRMacIver: this is the kind of source I got this from: http://debasishg.blogspot.com/2006/03/non-java-languages-on-jvm.html |
| 15:40:26 | <lambdabot> | Title: Ruminations of a Programmer: Non Java Languages on the JVM, http://tinyurl.com/65am4l |
| 15:40:49 | <vixey> | yeah maybe #haskell-blah |
| 15:40:53 | <jdh30> | they list three ways to implement tail calls. "Use of trampolines limit indefinite stack growth, but at the expense of performance, since all calls made by the trampoline are statically unknown method dispatches." |
| 15:40:55 | <DRMacIver> | Also, hotspot is basically a great big inlining machine, so nonlocal exceptions will often become local. |
| 15:41:11 | <[Justice]> | is the speed of throwing exceptions important? would fast exceptions mean that it's acceptable to use them to control program flow? |
| 15:41:34 | <Heffalump> | [Justice]: yes. See O'Caml for an example |
| 15:41:43 | <sclv> | @tell ndm If you're interested in the cgi testsuite I've been working on, here's its repo: http://code.haskell.org/~sclv/cgicheck/ |
| 15:41:43 | <lambdabot> | Consider it noted. |
| 15:41:44 | <DRMacIver> | [Justice]: In this case this is an implementation detail. It's often nice to be able to use them for compiler generated control flow. |
| 15:42:03 | <jdh30> | If you're throwing and catching an exception every time you make a tail call then you're looking at up to 30x performance degradation on current JVMs. So it is serious, yes. |
| 15:42:07 | <Heffalump> | and of course all the various kinds of Haskell exceptions, at least some of them are definitely fast, and they may well all be. |
| 15:43:01 | <jdh30> | Justice: Yes. OCaml uses exceptions extensively for ordinary control flow. Incidentally, this is probably the single biggest problem when porting OCaml code to F# where exceptions are 600x slower. You have to convert all of that exception-based control flow into explicit constructs. |
| 15:43:19 | <jdh30> | How are exceptions handled by GHC? |
| 15:43:21 | <[Justice]> | hmm |
| 15:43:33 | <vixey> | jdh30: "30x"? |
| 15:43:45 | <vixey> | jdh30: what are you measuring against are you just making up numbers |
| 15:44:18 | <Heffalump> | jdh30: depends on the kind of exception. I was thinking of explicit ones like Either. |
| 15:44:34 | <jdh30> | Exceptions can be that much slower on the JVM compared to OCaml. I'm assuming function calls are the same. |
| 15:44:38 | <[Justice]> | Either is an exception? |
| 15:44:54 | <Heffalump> | [Justice]: yes, Left for the exceptional values and Right for real values. |
| 15:44:56 | <jdh30> | Isn't either equivalent to returning a variant? |
| 15:45:08 | <jdh30> | So the performance is different between left and right? |
| 15:45:15 | <Heffalump> | variants have more options than either |
| 15:45:19 | <[Justice]> | that's not language/platform exceptions |
| 15:45:22 | <DRMacIver> | I don't have absolute numbers compared to normal returns, but if you take a look at Odersky's paper comparing two approaches to tail call optimisations, the one using exceptions isn't actually that much slower and is occasionally faster. |
| 15:45:41 | <Heffalump> | [Justice]: sure, but monads make them look quite like it |
| 15:45:54 | <Heffalump> | a lot of stuff in Haskell is in the libraries when it would be in the language in other languages |
| 15:46:02 | <[Justice]> | seems like everything's a monad in H |
| 15:46:17 | <DRMacIver> | Everything is a monad in most languages. Haskell just makes it explicit. :) |
| 15:46:25 | <DRMacIver> | (And lets you benefit from it) |
| 15:46:41 | <jdh30> | Odersky says 20x slower in sec 3.1 http://citeseer.ist.psu.edu/cache/papers/cs/22759/http:zSzzSzlampwww.epfl.chzSzpaperszSzbabel01.pdf/schinz01tail.pdf |
| 15:46:42 | <lambdabot> | http://tinyurl.com/5eqnze |
| 15:47:56 | <DRMacIver> | Specifically Odersky says "Here's this technique which we didn't use because it was 25 times slower than the standard version" |
| 15:48:17 | <jdh30> | Yes. |
| 15:48:43 | <DRMacIver> | In particular that version doesn't use exceptions at all... |
| 15:49:14 | <vixey> | I am not sure if this is a #java invasion :p |
| 15:49:29 | <jdh30> | Would you be interested in a Haskell for the JVM. :-) |
| 15:49:35 | <Heffalump> | it's a language implementation discussion |
| 15:49:39 | <mrd> | java is just trying to cash in on haskell popularity |
| 15:49:43 | <DRMacIver> | Well, it's a #language-implementations invasion which happens to be targeted at the JVM. |
| 15:49:45 | <jdh30> | lol |
| 15:49:50 | <vixey> | jdh30: that's why I read through lambdavm |
| 15:49:51 | <DRMacIver> | jdh30: lambdavm has been around for a while. |
| 15:49:55 | <vixey> | jdh30: didn't learn much |
| 15:49:57 | <Heffalump> | mrd: hmm. I think java is still a few orders of magnitude more popular than haskell :-) |
| 15:49:59 | <DRMacIver> | I don't think anyone uses it. :) |
| 15:50:04 | <mrd> | pfft |
| 15:50:09 | <DRMacIver> | Heffalump: Or at least a few orders of magnitude more *used* than Haskell. :) |
| 15:50:16 | <DRMacIver> | Not neccessarily the same thing. |
| 15:50:19 | <jdh30> | :-) |
| 15:50:42 | <Heffalump> | yes, Haskell is very popular with most people who use it. |
| 15:50:44 | <[Justice]> | someday soon, java will get rid of inner classes and support closures and tail calls |
| 15:50:45 | <DRMacIver> | jdh30: The relevant point here is that they compare two versions. One uses ordinary returns and one uses exceptions. The two are not noticably different in performance. |
| 15:50:47 | <Heffalump> | I guess that could make up for it :-) |
| 15:50:57 | <DRMacIver> | [Justice]: I *like* inner classes. |
| 15:51:05 | <vixey> | or you could just program in Scheme |
| 15:51:11 | <Heffalump> | inner classes give you closures, right? |
| 15:51:14 | <DRMacIver> | The fact that they're a shitty substitute for first class functions doesn't mean they're a bad feature. |
| 15:51:22 | <vixey> | it's a lot easier to write Scheme in Scheme than Scheme in Java |
| 15:51:25 | <jdh30> | No. He failed to observe a difference but measuring the wrong thing. Look at his benchmarks: tail calls weren't even relevant for the first three! |
| 15:51:29 | <geezusfreeek> | java? dangit i want some coffee |
| 15:51:56 | <jdh30> | Do inner classes automate closing of the environment? |
| 15:52:06 | <[Justice]> | sort of, yes |
| 15:52:20 | <vixey> | jdh30: yes that's why they are innerclasses |
| 15:52:27 | <vixey> | (rather than just normal classes) |
| 15:52:40 | <vixey> | (but this is kind of offtopic) |
| 15:52:55 | <[Justice]> | bringing it back on topic, i hear H is getting inner classes |
| 15:52:59 | <jdh30> | If you want to stress test Odersky's implementation you need to run a program that performs alternative tail and non-tail calls. He didn't do that so his results don't show the worse-case behaviour. |
| 15:53:10 | <vixey> | [Justice]: "H" is what? |
| 15:53:16 | <[Justice]> | Haskell |
| 15:53:42 | <DRMacIver> | jdh30: It's not really relevant. The approach shrinks the stack at a fixed depth regardless of how you reach that depth. |
| 15:53:43 | <geezusfreeek> | ... |
| 15:53:51 | <Heffalump> | [Justice]: if you mean associated types, then sort of. |
| 15:54:11 | <jdh30> | But he optimized repeated tail-only calls and then benchmarked only that, AFAICT. |
| 15:54:15 | <geezusfreeek> | i don't think that's the same at all |
| 15:54:31 | <DRMacIver> | It's basically the usual continuation based approach of "make everything a tail call then shrink the stack at a fixed depth" |
| 15:54:51 | <DRMacIver> | I think. It's been a while since I've actually read this paper. |
| 15:55:07 | <augustss_> | DRMacIver: is this for Scala? |
| 15:55:21 | <DRMacIver> | augustss_: No, Scala's tail call optimisation is kinda feeble. This is for his previous work. |
| 15:55:32 | <augustss_> | oh, ok |
| 15:55:37 | <Heffalump> | geezusfreeek: it gives you the possibility to make "inner type classes" via a bit of a hack (with wrapping up contexts) |
| 15:55:50 | <jdh30> | That also begs the question: why did he give up on tail calls if they worked so well? |
| 15:56:00 | <jdh30> | hi lennart |
| 15:56:04 | <augustss_> | hi |
| 15:56:14 | <DRMacIver> | jdh30: They didn't work so well. I'm just using this to demonstrate the reletive performance of exceptions and returns. |
| 15:56:16 | <geezusfreeek> | Heffalump: hmm. i didn't realize that. |
| 15:56:47 | <jdh30> | But you can measure the relative performance really easily? |
| 15:56:58 | <sclv> | whoa (vis a vis inner type classes) |
| 15:57:20 | <DRMacIver> | Measuring performance on the JVM is never easy. :) |
| 15:57:23 | <augustss_> | hmmm, what does inner type classes even mean? |
| 15:57:27 | <[Justice]> | finally, scared someone! no inner classes in haskell, sorry |
| 15:57:32 | <sclv> | I feel like when ATs start to get real use I'll have to learn haskell all over again. |
| 15:57:54 | <geezusfreeek> | [Justice]: if you mean me then you are mistaken :P i didn't believe you for a second |
| 15:58:01 | <jdh30> | There is another problem. The exception optimizations you referred to only work well when the exception does not carry any associated data. |
| 15:58:02 | <Heffalump> | augustss_: well, I was arbitrarily taking it to mean the same thing as what "associated type classes" would mean if they existed. |
| 15:58:21 | <jdh30> | Maybe you can work around that by using a global mutable though... |
| 15:58:28 | <DRMacIver> | jdh30: No, it works pretty well even with the associated data. |
| 15:58:42 | <jdh30> | Only if the data is static. |
| 15:58:45 | <DRMacIver> | No |
| 15:58:49 | <jdh30> | Which it isn't here. |
| 15:58:55 | <Heffalump> | push the data and jump to the handler, surely? |
| 15:58:58 | <DRMacIver> | It's perfectly legit to allocate a new exception with the data each time. |
| 15:59:03 | <jdh30> | It certainly didn't work when I tested it. |
| 15:59:13 | <Heffalump> | or rather, put the data on the stack after unwinding the stack back to the handler |
| 15:59:29 | <DRMacIver> | You almost certainly weren't suppressing stack trace generation then. |
| 15:59:33 | <Heffalump> | (where unwind = modify the stack pointer by the relevant number) |
| 16:00:05 | <DRMacIver> | http://blogs.sun.com/jrose/entry/longjumps_considered_inexpensive |
| 16:00:12 | <jdh30> | Conflicts with verification and the concurrent GC make the implementation complicated IIRC. I'm sure I can dig out the code. |
| 16:00:19 | <jdh30> | Yes, that was the exact article I was working from. |
| 16:00:39 | <Heffalump> | why would an implementation trick conflict with verification? You verify first, then run. |
| 16:00:47 | <jdh30> | There is a workaround where you statically allocate an exception with dummy data and use cloning instead... |
| 16:02:02 | <Heffalump> | I thought DRMacIver was saying that there is a way to turn off stack trace generation, which would negate the whole thing about it being expensive? |
| 16:02:11 | <DRMacIver> | There is. It's mentioned in the comments there. |
| 16:02:21 | <DRMacIver> | Here's a larger article about it: http://www.javaspecialists.co.za/archive/Issue129.html |
| 16:02:23 | <lambdabot> | Title: [JavaSpecialists 129] - Fast Exceptions in RIFE |
| 16:02:51 | <Heffalump> | is fillInStackTrace part of the standard? That's quite nice, if so. |
| 16:02:56 | <DRMacIver> | In particular note the comparison between throwing a new exception and throwing a preallocated one. |
| 16:02:59 | <DRMacIver> | Heffalump: Yes |
| 16:03:04 | <DRMacIver> | It's just a native method on Throwable |
| 16:03:32 | <Heffalump> | does the JIT actually notice that you overrode it and do any extra clever stuff? (beyond the gain of not having to actually run it) |
| 16:03:34 | <DRMacIver> | And thus is specified along with the rest of the standard library |
| 16:03:40 | <DRMacIver> | Not that I know of |
| 16:03:50 | <DRMacIver> | But the gain of not having to actually run it is kinda huge |
| 16:03:51 | <Heffalump> | I guess there could always be an unchecked exception. |
| 16:04:17 | <jdh30> | Why? I never understood that. Why are exceptions so much slower on the JVM and .NET? |
| 16:04:21 | <DRMacIver> | Because it basically has to perform some really nastily slow stack inspection in the standard implementation. |
| 16:04:34 | <sclv> | that trick is quite nice. |
| 16:05:01 | <jdh30> | Why do other language implementations like OCaml not have to do that? |
| 16:05:12 | <Heffalump> | they don't offer stack introspection |
| 16:05:19 | <DRMacIver> | Well, OCaml doesn't do stack traces in the same way. |
| 16:05:28 | <Heffalump> | the JVM and .NET offer it both for stack traces and for security policies (I think) |
| 16:05:57 | <DRMacIver> | On top of that, I think a large part of it is because the JVM and .NET use a very C-like stack and lose some optimisation potential as a result |
| 16:06:10 | <jdh30> | OCaml has stack traces but no security. |
| 16:06:11 | <jdh30> | interesting |
| 16:06:19 | <sclv> | @go stackless python |
| 16:06:20 | <[Justice]> | stack introspection is very nice when your code is wrong ... so you get slower exceptions in development and test, but then you don't throw any exceptions in the first place (hopefully) when your code is out in the wild |
| 16:06:21 | <lambdabot> | http://www.stackless.com/ |
| 16:06:21 | <lambdabot> | Title: Stackless.com - About Stackless |
| 16:06:22 | <vixey> | "no security"? |
| 16:06:28 | <vixey> | I guess type safety doesn't mean anything? |
| 16:06:53 | <Heffalump> | jdh30: under what circumstances does it provide stack traces? |
| 16:06:54 | <jdh30> | Not in this context, no. |
| 16:06:58 | <sclv> | vixey: the JVM has a very fancy security policy for running untrusted code with various levels of sandboxing. |
| 16:07:05 | <DRMacIver> | In particular if you have a continuations based implementation (I don't know if either Haskell or OCaml do) then you can treat exception throwing as basically just another type of return. |
| 16:07:15 | <Heffalump> | in principle that kind of thing can be expressed in types, but in practice it isn't |
| 16:07:41 | <mar77a> | > 7 * 5 |
| 16:07:43 | <lambdabot> | 35 |
| 16:08:32 | <DRMacIver> | (I seem to recall that stack frames are heap allocated in OCaml, which probably helps in a similar way) |
| 16:08:54 | <nolrai_> | >zipWith take [1..] [x..] :: http://en.wikipedia.org/wiki/Special:Search?go=Go&search=Expr |
| 16:09:08 | <vixey> | nolrai_: lol |
| 16:09:30 | <nolrai_> | bwuag!? |
| 16:09:47 | <nolrai_> | > zipWith take [1..] [x..] :: [ [Expr] ] |
| 16:09:47 | <lambdabot> | Couldn't match expected type `[Expr]' against inferred type `Expr' |
| 16:10:02 | <[Justice]> | > take 5 $ zipWith take [1..] [1..] |
| 16:10:03 | <lambdabot> | add an instance declaration for (Enum [a], Num [a]) |
| 16:10:04 | <vixey> | > [x..] :: [Expr] |
| 16:10:05 | <lambdabot> | [Exception: not a number |
| 16:10:16 | <jdh30> | Incidentally, I'd like to make some parallel benchmarks for OCaml, Haskell and F#. Anyone interested in helping? |
| 16:10:30 | <jdh30> | Does Haskell have a parallel tree-based set implementation? |
| 16:10:42 | <nolrai_> | > zipWith take [1..] ['a' ..] |
| 16:10:43 | <lambdabot> | Couldn't match expected type `[a]' against inferred type `Char' |
| 16:11:00 | <Heffalump> | jdh30: what do you mean by parallel in that context? |
| 16:11:08 | <vixey> | > iterate (drop 1) ['a'..] |
| 16:11:09 | <lambdabot> | ["abcdefghijklmnopqrstuvwxyz{|}~\DEL\128\129\130\131\132\133\134\135\136\137... |
| 16:11:12 | <BONUS> | > zipWith take [1..] [['a'..]] |
| 16:11:13 | <lambdabot> | ["a"] |
| 16:11:21 | <jdh30> | As in benefitting from multicore (but not embarassingly parallel). |
| 16:11:34 | <Heffalump> | wouldn't a tree-based implementation be parallel by default, in the sense of supporting access from multiple threads at once? |
| 16:11:35 | <nolrai_> | vixey: thats it. |
| 16:11:38 | <vixey> | > map (take 3) . iterate (drop 1) $ ['a'..] |
| 16:11:39 | <lambdabot> | ["abc","bcd","cde","def","efg","fgh","ghi","hij","ijk","jkl","klm","lmn","mn... |
| 16:12:06 | <jdh30> | I'm looking for a set union implementation that automatically distributes itself over multiple cores. |
| 16:12:17 | <Heffalump> | oh, right |
| 16:12:21 | <Twinside> | jdh30 > I remember some benchmark done to compare OCaml and F# in a french developer's forum, they got many issue because OCaml's Garbage COllector is not thread safe |
| 16:12:22 | <Heffalump> | no, then |
| 16:12:33 | <[Justice]> | > do { x <- Left 10 ; return "ABC" } |
| 16:12:34 | <lambdabot> | Add a type signature |
| 16:12:44 | <jdh30> | Yes. OCaml will definitely lose until it gets its parallel GC this summer... |
| 16:12:49 | <jdh30> | really? |
| 16:13:05 | <[Justice]> | > do { x <- Nothing ; return "ABC" } |
| 16:13:06 | <lambdabot> | Nothing |
| 16:13:10 | <Twinside> | i'm searching the link |
| 16:13:16 | <jdh30> | i thought the Haskell stdlib would be automagically parallelized... |
| 16:13:16 | <BONUS> | > map (take 3) . tails $ ['a'..] |
| 16:13:18 | <lambdabot> | ["abc","bcd","cde","def","efg","fgh","ghi","hij","ijk","jkl","klm","lmn","mn... |
| 16:13:26 | <Heffalump> | jdh30: why did you think that? |
| 16:13:50 | <malebria> | Good afternoon. |
| 16:13:51 | <Heffalump> | > do { x <- Left "boo!" ; return "ABC" } |
| 16:13:53 | <lambdabot> | Left "boo!" |
| 16:13:56 | <vixey> | hi |
| 16:13:58 | <jdh30> | I assumed Haskellers would be very keen to leverage their shiny new multicores. |
| 16:14:04 | <DRMacIver> | Because the web is full of lies and deceit about "Purely functional means you can automagically parallelise!!" |
| 16:14:06 | <sclv> | jdh: nothing in the haskell stdlibs is auto-parallelized. |
| 16:14:13 | <Heffalump> | yes, but automagic paralellization is hard.. |
| 16:14:17 | <DRMacIver> | Usually from people who don't know what they're talking about. |
| 16:14:21 | <malebria> | > (\x -> y where y = x * 2) 2 |
| 16:14:21 | <lambdabot> | Parse error at "where" (column 10) |
| 16:14:24 | <jdh30> | Really? Oh bloody hell that sucks. |
| 16:14:32 | <malebria> | Is it not possible to use where inside of lambda notation? |
| 16:14:36 | <malebria> | Or am I missing something? |
| 16:14:38 | <Heffalump> | jdh30: you didn't know that automagic parallelization is hard??? |
| 16:14:40 | <BONUS> | use let |
| 16:14:47 | <vixey> | malebria: You can't use where at all with lambdabot |
| 16:14:51 | <Heffalump> | malebria: where applies to declarations, not expressions |
| 16:14:55 | <[Justice]> | > (\ x -> y where { y = x * 2 }) 2 |
| 16:14:55 | <lambdabot> | Parse error at "where" (column 11) |
| 16:14:56 | <jdh30> | I know automagic parallelization is easy in F#. :-) |
| 16:15:00 | <Heffalump> | the thing immediately inside a lambda is an expression |
| 16:15:02 | <sclv> | writing a set union in parallel that is across-the-board more performance seems tricky. |
| 16:15:06 | <DRMacIver> | As I recall there's been research that basically shows that there's very little room for automatic parallelisation even in purely functional code. |
| 16:15:12 | <Heffalump> | jdh30: it is? how? |
| 16:15:14 | <BONUS> | > (\x -> let y = x * 2 in y) 2 |
| 16:15:15 | <lambdabot> | 4 |
| 16:15:17 | <sclv> | s/performance/performant/ |
| 16:15:24 | <jdh30> | The next versions of both of our F# libraries are parallel and it was quite easy (with MS's TPL CTP) and I'd assumed the same would be true of Haskell. |
| 16:15:32 | <malebria> | Heffalump: hum, I think I got the point. |
| 16:15:35 | <sclv> | writing a unions function across n sets that parallelizes is easy, though... |
| 16:15:40 | <Heffalump> | jdh30: in what way is that automagic? |
| 16:16:06 | <Heffalump> | is the code online somewhere? I'd like to understand what precise kind of parallelization you mean. |
| 16:16:08 | <sclv> | (we could, e.g., turn our mergesort parallel too, but the question is how often it would actually be a win) |
| 16:16:12 | <jdh30> | sclv: that is actually what I want: map reduce over sets where the reduce operation is set union. |
| 16:16:34 | <jdh30> | you mean the source code to our products? No, that isn't on-line. :-) |
| 16:16:39 | <sclv> | oh -- not over just two sets, but over a whole bunch. yeah. that's a one liner. |
| 16:16:42 | <pejo> | DRMacIver, Satnam Singh and some other people had a paper at ICFP (2007?) that showed very little gain in practice, but in theory a bunch of sequential stuff from nofib could be quite parallel. |
| 16:16:50 | <sclv> | its just not the default. |
| 16:16:53 | <jdh30> | Not quite a one-liner, but it is easy enough. |
| 16:17:03 | <sclv> | jdh30: in haskell it is a one liner. |
| 16:17:09 | <jdh30> | :-) |
| 16:17:12 | <sclv> | ?hoogle parMap |
| 16:17:12 | <lambdabot> | Control.Parallel.Strategies.parMap :: Strategy b -> (a -> b) -> [a] -> [b] |
| 16:17:44 | <DRMacIver> | pejo: Ah. That's probably what I'm thinking of. |
| 16:17:50 | <Heffalump> | none of this is automagic, that's the key point. Automagic parallelization doesn't work because compilers don't know what's expensive. |
| 16:17:56 | <jdh30> | The basic idea is to convey a cost function that gives the approximate number of operations (or time) required for a sub computation. Then you use that to control whether or not divide and conquor algorithms spawn subtasks in parallel or resort to single threaded code. |
| 16:17:59 | <Heffalump> | And F# doesn't have it any more than Haskell does. |
| 16:18:26 | <jdh30> | Sure. You have to write it yourself but that covers a lot of practically-important applications. |
| 16:18:29 | <Heffalump> | jdh30: right, that's the kind of thing data parallel Haskell does (or will do when it works properly) |
| 16:18:32 | <Codex_> | can we just make compilers know what's expensive? :) |
| 16:18:46 | <Baughn> | Codex_: Not if we don't know it ourselves |
| 16:18:53 | <jdh30> | Codex_: Intel's Fortran compiler is actually already quite clever in that respect. |
| 16:18:55 | <Heffalump> | putting cost into the type system might be neat |
| 16:18:57 | <Baughn> | Though some runtime optimization would be nice |
| 16:19:06 | <pejo> | Codex, that's very hard, as Heffalump just said. |
| 16:19:13 | <Baughn> | Heffalump: How? The cost usually depends on the /size/ of the input data |
| 16:19:15 | <EvilTerran> | Baughn, :O that's crazy talk! |
| 16:19:20 | <Heffalump> | Baughn: polymorphism |
| 16:19:37 | <Heffalump> | if the input data is size x, the output is size 2x and takes 3x time to produce. |
| 16:19:40 | <Heffalump> | That kind of thing. |
| 16:19:49 | <jdh30> | Yes. The compiler injects run-time dispatches (when it knows they are cheap) that dispatch to parallel code for large input (= long arrays in Fortran). |
| 16:19:56 | <sclv> | haha and track the input size with type-level nats! |
| 16:19:59 | <Heffalump> | I'm just speculating wildly, I'm sure it's really hard in practice too. |
| 16:20:30 | <jdh30> | It detects O(x^n) complexity for simple nested functions (e.g. rectangular or triangular) and acts accordingly. |
| 16:20:34 | <Heffalump> | jdh30: for user-written functions, or just specific library functions? |
| 16:20:45 | <jdh30> | Library specific functions only. |
| 16:20:57 | <jdh30> | assuming you're talking about what we were talking about. :-) |
| 16:21:00 | <Heffalump> | ah, that's not very interesting (although still quite useful in practice, no doubt) |
| 16:21:05 | <mtag55> | i have a list defined like list = [1,2,3,etc] and i want to change an element like list !! 2 = 124 |
| 16:21:06 | <jdh30> | Absolutely. |
| 16:21:10 | <mtag55> | how can i do that? |
| 16:21:14 | <mar77a> | :t elems |
| 16:21:16 | <lambdabot> | forall i e. (Ix i) => Array i e -> [e] |
| 16:21:37 | <jdh30> | So what 3rd party Haskell libraries have been parallelized? |
| 16:21:43 | <Heffalump> | it's kind of the moral equivalent of having the compiler implement strcpy/memcpy. |
| 16:21:46 | <EvilTerran> | mtag55, there isn't a builtin for it |
| 16:22:25 | <jdh30> | If the compiler does it, yes. I was originally talking about the moral equivalent of calling memcpy yourself. ;-) |
| 16:22:25 | <EvilTerran> | mtag55, however, i think you should be able to implement it without resorting to explicit recursion |
| 16:22:26 | <Baughn> | mtag55: You'll need to copy the list up to the element you want to change, and then you can share the rest |
| 16:22:57 | <Heffalump> | compilers often recognise memory copy loops and change it to the library call. |
| 16:22:58 | <Baughn> | mtag55: If that's a common operation, may I suggest you use IntMap instead? Or maybe starray, or map, or... yeah, lots of options. |
| 16:23:02 | <jdh30> | DRMacIver: what gave you the impression that ocaml heap allocated stack frames? |
| 16:23:15 | <jdh30> | Yes. |
| 16:23:17 | <mtag55> | ok |
| 16:23:18 | <mtag55> | tnx |
| 16:23:38 | <EvilTerran> | mtag55, Baughn has a good point. O(ix) to change the ix'th element of a list |
| 16:23:40 | <jdh30> | A lot of compilers claim to do such things but suck at them. SGI's Fortran compiler for one... |
| 16:24:12 | <DRMacIver> | jdh30: Good question. I believe it's a commonly used approach in SML compilers and assumed OCaml did similarly. I vaguely recall I might have had some more specific reason but could be totally wrong. |
| 16:24:23 | <Heffalump> | ARM's C++ compiler does automatic vectorization |
| 16:24:44 | <Botje> | @src maybeToList |
| 16:24:45 | <lambdabot> | maybeToList Nothing = [] |
| 16:24:45 | <lambdabot> | maybeToList (Just x) = [x] |
| 16:24:50 | <jdh30> | Heffalump: is that just what the salesman said or do you know that it works? |
| 16:24:51 | <Botje> | @src listToMaybe |
| 16:24:51 | <lambdabot> | listToMaybe [] = Nothing |
| 16:24:52 | <lambdabot> | listToMaybe (a:_) = Just a |
| 16:24:55 | <Botje> | okay :) |
| 16:25:03 | <Baughn> | mtag55: If you change elements of a list often, you're doing something wrong. |
| 16:25:08 | <Heffalump> | jdh30: I know that it works. |
| 16:25:15 | <jdh30> | Ah, very interesting. |
| 16:25:22 | <Heffalump> | I think you still have to pay extra for it, though. |
| 16:25:24 | <EvilTerran> | mtag55, another possibility would be to replace your [a] with a [STRef a], thus rendering the cells mutable |
| 16:25:29 | <Baughn> | mtag55: (Unless they're always close to the head, in which case the cost is O(1) |
| 16:25:41 | <jdh30> | Yes. ARM are very good at business as well as technology. :-) |
| 16:25:53 | <EvilTerran> | mtag55, but that'd only be the best option very occasionally |
| 16:26:01 | <jdh30> | Ok. Here is another crazy idea. |
| 16:26:02 | <Baughn> | mtag55: Evilterran has a point, too, though STArray would have less overhead - but we really don't know enough about your program to say |
| 16:26:09 | <Heffalump> | actually I think they're very good at milking an early success for all its worth |
| 16:26:20 | <jdh30> | That's the same thing. ;-) |
| 16:26:29 | <mtag55> | i don't know what STArray is |
| 16:26:30 | <EvilTerran> | indeed. i was just about to mention Data.Array.ST.STArray |
| 16:26:52 | <Heffalump> | it doesn't imply that they continue to build good technology consistently (though they do in some cases, certainly) |
| 16:26:54 | <mtag55> | i want to find the minimum within a matrix and change it |
| 16:27:04 | <DRMacIver> | The talk about fortran reminds me of something I've been wondering: How much fun you could have with compiler optimisations using some combination of fortran and Haskell feature sets. e.g. if you had a language with a very restricted set of datatypes (say: numerics, records, arrays) + more semantic restrictions (maybe only allowing tail recursion + some fixed combinators), but it was purely functional, had higher order functions, etc. |
| 16:27:06 | <jdh30> | If GHC had a commerce-friendly intermediate representation like DLLs, could it be used to create a commercial platform where people buy and sell Haskell libraries? |
| 16:27:15 | <EvilTerran> | mtag55, the ST monad is like the IO monad, except with only mutable values (called STRefs) and no other side-effects |
| 16:27:17 | <Baughn> | mtag55: STArray is, basically, a mutable array type. A type trick allows you to embed imperative array-mutating code deep inside functional code |
| 16:27:25 | <DRMacIver> | The GHC array fusion stuff seems to suggest you can do an awful lot for optimising purely functional array code. |
| 16:27:30 | <Heffalump> | jdh30: "like DLLs"? as in DLLs, or something different? |
| 16:27:41 | <Heffalump> | it'll get proper DLL support in 6.10, AIUI. |
| 16:27:42 | <DRMacIver> | And something like clean's uniqueness typing might be a win here too. |
| 16:27:44 | <EvilTerran> | mtag55, which means that it's impossible for side-effects to escape the monadic action where the mutability is contained |
| 16:27:46 | <jdh30> | Managed code DLLs, like our F# products. |
| 16:28:12 | <Baughn> | mtag55: And then there are zippers. Using one of those (google it) allows you to change any data structure repeatedly in the same spot for O(1) cost, but means /moving/ through the structure gets more expensive |
| 16:28:26 | <Heffalump> | http://www.arm.com/products/DevTools/RVCT.html has an example of the kind of vectorization it does, btw |
| 16:28:27 | <lambdabot> | Title: RealView Compilation Tools |
| 16:28:36 | <jdh30> | That's really my single biggest gripe with OCaml: that it is not viable as a commercial platform. I don't believe that will ever be addressed but I spoke to SPJ about this in the context of Haskell and he was interested in the idea. |
| 16:28:48 | <Heffalump> | jdh30: that requires inventing a whole concept of managed code (and therefore a VM), right? |
| 16:29:04 | <gubagem> | why isnt ocaml viable as a commerical product/platform? |
| 16:29:12 | <vixey> | "not viable as a commercial platform" -- not true |
| 16:29:14 | <jdh30> | Heffalump: I have no idea. |
| 16:29:19 | <Heffalump> | some people care about binary libraries. |
| 16:29:21 | <vixey> | gubagem: it is |
| 16:29:26 | <vixey> | gubagem: that's a blatant lie |
| 16:29:31 | <Heffalump> | More so in the commercial world than in the OS world. But not universally. |
| 16:29:41 | <jdh30> | gubagem: you cannot create a market where people can buy and sell OCaml libraries because of the limitations of the language implementation. |
| 16:29:47 | <gubagem> | oh, is haskell viable as a 'commerical platform' |
| 16:29:47 | <Heffalump> | jdh30: I'm just trying to understand what you mean. |
| 16:29:48 | <EvilTerran> | mtag55, hmm? |
| 16:29:56 | <Baughn> | mtag55: For your particular case of a list, a zipper means just keeping /two/ lists - "ahead" and "behind" - and moving elements from one to the other when you move through the list. Obviously you can then alter the element at the "cursor" easily |
| 16:30:00 | <Heffalump> | If you just mean DLLs, then what does the "Managed code" bit mean? |
| 16:30:08 | <jdh30> | gubagem: Haskell is not yet AFAIK. |
| 16:30:19 | <obk> | ACTION has a program that goes into an endless loop, *unless* it is run in the debugger - in which case it works fine. ????? |
| 16:30:28 | <Heffalump> | jdh30: only by your rather restricted definition of "commercial" |
| 16:30:28 | <jdh30> | gubagem: for exactly the same reasons. However, Haskell is not dead from an evolutionary perspective... |
| 16:30:33 | <DRMacIver> | Binary libraries aren't the only way to go. Source licenses are totally acceptable. |
| 16:30:42 | <Baughn> | obk: Fun. Define "endless loop"; also, does it use any concurrency? |
| 16:30:45 | <Heffalump> | DRMacIver: not everyone thinks that. |
| 16:30:56 | <Heffalump> | also, binary distribution is important in some environments |
| 16:31:01 | <Baughn> | obk: (Eg. 100% cpu use loop, 0% use hang, or <<LOOOP>> exception) |
| 16:31:02 | <gubagem> | i am just learning haskell and i havent seen the line savings yet, then again im passing around lists as state |
| 16:31:03 | <obk> | Baughn: Nope. Normal "sequential" code. It just hangs in the middle |
| 16:31:04 | <Heffalump> | even internally to a cmopany |
| 16:31:07 | <DRMacIver> | Indeed. But "not everyone likes that" is not the same as "not commercially viable" |
| 16:31:19 | <cjb> | Heffalump: a company that doesn't trust its employees, I guess? |
| 16:31:19 | <Heffalump> | DRMacIver: yes, indeed. |
| 16:31:20 | <Baughn> | obk: Try compiling it with -threaded and see what happens |
| 16:31:23 | <mtag55> | you gave me headacke :P |
| 16:31:32 | <obk> | 100% CPU, yes |
| 16:31:32 | <mtag55> | many new information for a newbie |
| 16:31:33 | <Baughn> | obk: (That turns on extra deadlock detection code, among other things) |
| 16:31:36 | <Heffalump> | cjb: not exactly. A company that can't afford to be compiling on every employee's desktop. |
| 16:31:40 | <DRMacIver> | I'm not saying that having libraries distributable as binaries isn't a good thing. It obviously is. I'm just saying it isn't essential. |
| 16:31:45 | <obk> | ACTION will try |
| 16:31:50 | <Baughn> | obk: Oh. Then it's not a hang, and -threaded won't help. Can try, but.. |
| 16:31:56 | <DRMacIver> | And being able to distribute application binaries is distinct from being able to distribute library binaries |
| 16:32:08 | <cjb> | Heffalump: Oh, I see. |
| 16:32:13 | <Heffalump> | yep (but every language supports that, so it doesn't really matter) |
| 16:32:17 | <Baughn> | obk: I think, at this point, you need to paste the code. And preferably point out which line causes the loop. ;) |
| 16:32:26 | <pejo> | cjb, having an *identical* binary saves a great deal of pain when trying to reproduce errors. |
| 16:32:29 | <DRMacIver> | Well, every language other than all the ones which are source interpreted only. :) |
| 16:32:38 | <Heffalump> | cjb: COM was very successful in certain areas precisely because of this. |
| 16:32:54 | <obk> | Baughn: ha ha. If I knew that... |
| 16:32:55 | <Heffalump> | and in some senses .NET is the natural follow-on to COM. |
| 16:32:56 | <DRMacIver> | But my point was that it's not a case of compiling on *everyone's* desktop, just the developers. :) |
| 16:33:11 | <obk> | The program isn't excatly small :-( |
| 16:33:30 | <jdh30> | Heffalump: managed code DLLs have a safe high-level interface. |
| 16:33:33 | <Heffalump> | DRMacIver: if everyone's desktop can in principle have different combinations of versions, then they all need to compile, or you need binary libraries. |
| 16:34:01 | <obk> | -threaded didn't help, as expected |
| 16:34:07 | <Heffalump> | jdh30: safe against what? Malicious code, or just broken code? (In what way is the C calling convention not safe, for the purposes of this discussion?) |
| 16:34:41 | <gubagem> | obk: do you know which part has the infinite loop? if so through in some I/O and see if its still infinite outside of the debugger |
| 16:35:07 | <Heffalump> | for safety against broken code, you just need some metadata + the C calling convention. GHC is getting pretty close to having that AIUI. |
| 16:35:09 | <jdh30> | DRMacIver: we also sell source licences. |
| 16:35:14 | <DRMacIver> | Heffalump: Hm. I don't follow. |
| 16:35:14 | <Baughn> | obk: If it's at 100% cpu you could throw the profiler at it |
| 16:35:21 | <Heffalump> | For safety against malicious code, you need a verification step. Which implies a VM, or PCC. |
| 16:35:26 | <obk> | gubagem: I guess I can do binary search for the offending loop (in fact have started doing so before hittong on the bright idea of using the debugger) |
| 16:35:39 | <jdh30> | Heffalump: I meant safe against broken code (i.e. no segfaults) but the JVM and .NET also try to provide security against malicious code. |
| 16:35:51 | <obk> | The profiler will work even if I kill the program with ^C right? That sounds like a plan... |
| 16:35:53 | <Heffalump> | DRMacIver: if your environment is built up from a big set of libraries, which each have multiple versions |
| 16:35:57 | <jdh30> | Heffalump: I'd be happy with safe against broken code. |
| 16:36:09 | <jdh30> | Heffalump: type safe DLLs. |
| 16:36:10 | <Heffalump> | then either you need binary libraries and binary compatibility, or you need to recompile for each combination of versions |
| 16:36:17 | <gubagem> | obk: isolate , tinker, get it to where it doesnt have the bug, then maybe reimplement the buggy part |
| 16:36:37 | <Heffalump> | jdh30: ok, so that's DLLs + a bit of metadata. As I say I don't think GHC is far off supporting that. |
| 16:36:37 | <obk> | Sure. I'm just stuck at "isolate" at the moment :-) |
| 16:36:49 | <vixey> | you don't need any types to be type safe |
| 16:36:59 | <vixey> | think about a haskell -> scheme translator |
| 16:37:10 | <Heffalump> | However you'll probably also want binary compatibility between code compiled with different GHC versions, and that's probably further off. |
| 16:37:24 | <gubagem> | obk: if you code allows it sprinkle with putStrLn's with little messages, and check and see what your variables really are doing |
| 16:37:27 | <jdh30> | Heffalump: Yes, I think it would be feasible to implement but is it possible to build a commercial market for Haskell libraries? |
| 16:37:30 | <malebria> | When I call forkProcess $ executeFile .... I get a defunct proccess left. |
| 16:37:38 | <malebria> | malebria 8129 0.0 0.0 0 0 pts/2 Z+ 13:27 0:00 \_ [aplay] <defunct> |
| 16:37:43 | <malebria> | I used it with aplay. |
| 16:37:44 | <Heffalump> | jdh30: No idea. You're the expert on selling libraries commercially. |
| 16:38:03 | <malebria> | Is something being made wrong? |
| 16:38:07 | <Heffalump> | I've never either wanted to do that or to buy them (either professionally or personally). |
| 16:38:09 | <geezusfreeek> | i would *guess* that such a market would be very small |
| 16:38:14 | <obk> | gubagem: Code is 99.99% pure, so it is more 'trace' than putStrLn, but yes that's what I've been doing. However, like I said, it isn't exactly small, so... :-( |
| 16:38:18 | <jdh30> | Heffalump: Well, I can tell you that we made £25 in three years of selling OCaml code and a hell of a lot more from F#. :-) |
| 16:38:20 | <geezusfreeek> | unfortunately :( |
| 16:38:38 | <Heffalump> | who do you sell to (in general terms)? |
| 16:38:38 | <Baughn> | obk: As I said, you should be able to get some use from the profiler |
| 16:38:41 | <jdh30> | vixey: yes about type safe. |
| 16:38:49 | <Baughn> | obk: Any infinite loop is going to show up on that. ;) |
| 16:38:58 | <jdh30> | Heffalump: I am happy to sell to anyone with money. :-) |
| 16:39:16 | <Heffalump> | jdh30: no doubt, but where did you get the £25 and the "hell of a lot more" from? :-) |
| 16:39:26 | <obk> | Baughn: Installing the prof libraries as we speak. This will take a few minutes... |
| 16:39:29 | <jdh30> | Heffalump: technical computing is our traditional market because I can do that with my eyes closed and we have a name in it but all ideas are welcome. :-) |
| 16:39:41 | <gubagem> | how do i turn a String into an Integer |
| 16:39:46 | <obk> | Interesting that it avoids the loop in the debugger though. When I figure it out I'll let you know. |
| 16:39:48 | <[Justice]> | :t read |
| 16:39:49 | <Heffalump> | jdh30: right, but what kind of person/institution buys your code? |
| 16:39:49 | <opqdonut> | gubagem: read |
| 16:39:50 | <lambdabot> | forall a. (Read a) => String -> a |
| 16:39:53 | <vixey> | :t read :: String -> Integer |
| 16:39:55 | <lambdabot> | String -> Integer |
| 16:39:55 | <gubagem> | oh yea |
| 16:39:57 | <Baughn> | obk: You don't actually need profiling libraries to profile your own code, although it's mre important in haskell than some other languages |
| 16:39:57 | <DRMacIver> | I've only come across one library I'd be willing to pay for, though I think there are a few more if my needs were specialised. The problem with libraries is that in order to be commercially viable they have to be kinda niche |
| 16:39:57 | <gubagem> | thx |
| 16:40:06 | <DRMacIver> | Niche or really hard to do right |
| 16:40:16 | <jdh30> | Heffalump: Ah, we sold one copy of Presenta (our technical presentation software written entirely in OCaml) but shelved it because it was so unreliable. We've sold lots of copies of F# for Numerics and F# for Visualization already. |
| 16:40:18 | <Heffalump> | nag is a good example of a library with fairly broad appeal |
| 16:40:20 | <obk> | I mean the base profiling libraries - won't link without them |
| 16:40:21 | <Baughn> | obk: And yes, please do. It's undoubtedly some sort of bug; they're supposed to act identically |
| 16:40:30 | <jdh30> | DRMacIver: Yes. |
| 16:40:41 | <DRMacIver> | (the one library is QT incidentally) |
| 16:40:51 | <DRMacIver> | (QT Jambi specifically) |
| 16:40:53 | <jdh30> | Heffalump: Yes. F# for Numerics is the new NAG. ;-) |
| 16:41:08 | <Heffalump> | jdh30: my question is who you sell to (in general terms describing the kind of institution or person, not specific names) |
| 16:41:15 | <jdh30> | DRMacIver: I also considered buying Qt but their demos segfaulted on my machine so I kept my money. |
| 16:41:29 | <Heffalump> | jdh30: is the low-level implementation in native code then? |
| 16:41:42 | <jdh30> | Heffalump: No, the low-level code is currently entirely F#. |
| 16:41:45 | <SamB> | Baughn: what have you been saying? |
| 16:41:51 | <Heffalump> | it'll be a while before it's the new NAG then :-) |
| 16:42:23 | <DRMacIver> | jdh30: One of the demos seg faults on my machine, but most of it works fine and the results are a lot better than any of the other GUI libraries I've looked at. |
| 16:42:31 | <DRMacIver> | (And the Jambi API is surprisingly pleasant) |
| 16:42:32 | <jdh30> | Heffalump: Performance-wise, yes. But it is vastly easier to use thanks to an elegant functional interface. |
| 16:42:33 | <SamB> | Baughn: the profiling RTS is not compatible with the non-profiling RTSs |
| 16:42:54 | <jdh30> | Heffalump: I'm not actually sure how to pigeon hole our software customers. |
| 16:43:02 | <Heffalump> | jdh30: no doubt. But NAG can just steal your market by making a similar interface, surely? |
| 16:43:12 | <jdh30> | Heffalump: I dissected the OCaml for Scientists customers accurately but I think that is quite difficult. |
| 16:43:15 | <SamB> | (in terms of compiled code, I mean) |
| 16:43:43 | <Heffalump> | jdh30: well, understanding the market is probably quite important when trying to work out if you might be able to sell something |
| 16:43:52 | <jdh30> | Heffalump: NAG could steal our interface but they would need to learn how to first and that would basically require them to give us a consultancy contract. :-) |
| 16:43:54 | <gubagem> | what does prelude.read : no parse mean? |
| 16:44:13 | <gubagem> | i believe im feeding read correct input...but it is just barfing out on me :( |
| 16:44:23 | <jdh30> | Heffalump: I believe our F# market is basically completely random. Composed almost entirely of tinkerers who just want something to play with. |
| 16:44:36 | <Heffalump> | jdh30: I didn't actually mean steal your specific interface, I just meant write a functional interface of their own. And they could do either by just hiring a functional programmer, surely? |
| 16:44:40 | <EvilTerran> | gubagem, maybe the return value of read's ending up the wrong type? |
| 16:44:46 | <[Justice]> | > read "10" :: Integer |
| 16:44:47 | <lambdabot> | 10 |
| 16:45:00 | <[Justice]> | > read "10" |
| 16:45:01 | <lambdabot> | Exception: Prelude.read: no parse |
| 16:45:02 | <malebria> | Shouldn't forkProcess be used then? |
| 16:45:03 | <jdh30> | Heffalump: If they could find a functional programmer versed in numerical methods, yes. But they don't exactly grow on trees. |
| 16:45:09 | <Heffalump> | jdh30: interesting. In my experience tinkerers don't spend money. |
| 16:45:21 | <SamB> | jdh30: what do they grow on? |
| 16:45:28 | <Heffalump> | quant groups :-) |
| 16:45:32 | <[Justice]> | make sure you specify what the resulting type should be |
| 16:45:33 | <cjb> | Heffalump: the .NET world is likely to be more amenable |
| 16:45:34 | <jdh30> | Heffalump: Right. I think that is really particular to Windows, where users expect to throw money at fun things. |
| 16:45:40 | <jdh30> | ROTFL |
| 16:45:57 | <cjb> | just as in the OS X world, people pay $30 for random pieces of shareware. |
| 16:46:12 | <jdh30> | Yes. We never managed to make any money out of OSX either... |
| 16:46:22 | <Heffalump> | jdh30: do you really think you need a deep understanding of numerical methods to write a good interface? |
| 16:46:23 | <SamB> | it's really unbelievable the stuff you have to pay for (or almost do) in Windows |
| 16:46:44 | <cjb> | SamB: e.g. WinZip |
| 16:46:53 | <jdh30> | Heffalump: Absolutely, yes. Not just a deep understanding of numerical methods (i.e. the functions themselves) but also how they are used. |
| 16:47:31 | <jdh30> | Mathematica is an excellent example of what good functional design can bring to technical computing but, of course, it is based around a grindingly-slow general term rewriter. |
| 16:47:31 | <Heffalump> | Fair enough. Though that requirement wouldn't stop a functional programmer stealing your interface :-) |
| 16:47:35 | <hpaste> | gubagem pasted "my offensive newbie code parse no read :-(" at http://hpaste.org/8019 |
| 16:48:21 | <jdh30> | Heffalump: Yes. Conversely, we can steal NAG's performance by licensing the Intel MKL and bundling it into F# for Numerics, just as the Extreme Optimization library for C# does. |
| 16:48:32 | <Heffalump> | and anyway I reckon that a functional programmer and a numerical methods expert working together would be able to do a good job, the knowledge doesn't need to be in one head |
| 16:48:41 | <jdh30> | Do many Haskellers use OSX? |
| 16:48:46 | <Heffalump> | yes, quite a few |
| 16:49:10 | <Baughn> | Enough that it works well on OS X (except opengl in ghci.. ;( |
| 16:49:13 | <Saizan> | gubagem: read for string expexcts it in quotes. |
| 16:49:22 | <Heffalump> | jdh30: matlab has a compiler, I wonder how well that works |
| 16:49:30 | <Saizan> | > read "\"foo\"" :: String |
| 16:49:32 | <lambdabot> | "foo" |
| 16:49:36 | <cjb> | Heffalump: goes to C, I think? |
| 16:49:43 | <Saizan> | > read "foo" :: String |
| 16:49:45 | <gubagem> | Saizan: uhhh how do i pass read just a String value then? |
| 16:49:45 | <lambdabot> | "Exception: Prelude.read: no parse |
| 16:49:54 | <Heffalump> | cjb: no doubt, but that's doesn't tell us much :-) |
| 16:49:57 | <jdh30> | Mathematica also has a compiler but it only compiles to an interpreted bytecode. I believe MATLAB's is much better. They gave me free copies so I should try them... :-) |
| 16:50:07 | <gubagem> | > read "1322"::Integer |
| 16:50:09 | <lambdabot> | 1322 |
| 16:50:22 | <Saizan> | gubagem: why use read at all for myName ? |
| 16:50:27 | <Baughn> | > read "42" -- It says "no parse". Curious; I wonder what it's defaulting to |
| 16:50:28 | <lambdabot> | Exception: Prelude.read: no parse |
| 16:50:40 | <gubagem> | cause im lazy and it looks nice :( |
| 16:50:50 | <cjb> | http://hogbaysoftware.com/products/writeroom is my favorite example of how OS X software works :) |
| 16:50:51 | <lambdabot> | Title: Writeroom |
| 16:51:08 | <cjb> | ("you want a text editor that can GO FULLSCREEN? that'll be $24.95, please.") |
| 16:51:13 | <Heffalump> | :-) |
| 16:51:33 | <Saizan> | gubagem: (head args) is sufficient, and you don't need a let for each variable |
| 16:51:42 | <Saizan> | Baughn: () |
| 16:51:48 | <gubagem> | > let myVar="happy happy joy joy" in read myVar::String |
| 16:51:50 | <Baughn> | > read "()" |
| 16:51:50 | <lambdabot> | "Exception: Prelude.read: no parse |
| 16:51:51 | <lambdabot> | () |
| 16:51:53 | <jdh30> | Wow. That application rocks. |
| 16:52:23 | <Baughn> | > let myVar = show "happy happy zombies" in read myVar :: String |
| 16:52:24 | <lambdabot> | "happy happy zombies" |
| 16:52:44 | <cjb> | hm, maybe I should make a writeroom.el |
| 16:52:45 | <jdh30> | Incidentally, few of our customers ever actually use what they buy. Some of them even buy multiple copies by accident... |
| 16:53:02 | <SamB> | jdh30: huh? |
| 16:53:16 | <cjb> | I don't think "go fullscreen and make the background black and the text green and a blinky block cursor" would be more than five lines of elisp :) |
| 16:53:22 | <Heffalump> | jdh30: that's an interesting business model you have |
| 16:53:26 | <SamB> | how do you know they don't use them? |
| 16:53:36 | <jdh30> | It wasn't deliberate. :-) |
| 16:53:45 | <Heffalump> | no, I didn't imagine it was :-) |
| 16:53:56 | <SamB> | that would be a silly business model |
| 16:53:57 | <Heffalump> | I think I'd be quite worried by it if it was me, though. |
| 16:53:59 | <jdh30> | They have individual logins and our web server says several have never been used. |
| 16:54:04 | <cjb> | jdh30: have you considered the options that bartending has to offer? |
| 16:54:26 | <DRMacIver> | cjb: It certainly guarantees that customers would use his products. |
| 16:54:34 | <cjb> | :) |
| 16:54:37 | <jdh30> | I found it quite worrying too so I tracked down some of the people and they explained that they had paid for something like a journal subscription and forgotten about it. |
| 16:54:48 | <jdh30> | When they were notified it had expired they just bought a new subscription. |
| 16:55:06 | <Heffalump> | so that's not quite buying the same product multiple times, is it? |
| 16:55:23 | <jdh30> | other people have bought multiple copies of one library for themselves as well. |
| 16:55:24 | <cjb> | It's leasing the same product multiple times. |
| 16:55:42 | <Heffalump> | jdh30: perhaps they think they need it to use them in parallel ;-) |
| 16:55:53 | <jdh30> | For the journals, yes. They've also done that for single user binary libraries. |
| 16:56:04 | <jdh30> | ROTFL. Yes, they must have had a dual core... :-) |
| 16:56:15 | <Heffalump> | isn't that the way M$ works these days? |
| 16:56:22 | <Heffalump> | get to enough cores and you have to spend more |
| 16:56:51 | <Baughn> | Heffalump: For values of "enough" that equal variously eight, four and /two/, yes |
| 16:56:59 | <jdh30> | It is really wierd though, and completely different from the OCaml world where people demand huge amounts of work for pennies. |
| 16:57:07 | <cjb> | Heffalump: Oracle, especially. |
| 16:57:09 | <DRMacIver> | Heffalump: It's the way Oracle works. :( |
| 16:57:17 | <pejo> | Heffalump, it's very much the way Oracle works |
| 16:57:22 | <cjb> | heh |
| 16:57:28 | <pejo> | Heh, stereo-quote seems apropriate. |
| 16:57:29 | <Heffalump> | I see this is a widely-felt sore point :-) |
| 16:57:32 | <DRMacIver> | Oracle's pricing model was written up by satan. |
| 16:57:42 | <jdh30> | Yes. I bought Windows XP Pro for £250 for my dual core. I am upgrading to eight cores and realised that I would need a new copy of Windows because my licence only covers 2 cores. |
| 16:57:42 | <DRMacIver> | There's no other explanation for it. |
| 16:57:50 | <Heffalump> | it seems mostly reasonable to me to make the charges proportional to the use |
| 16:58:01 | <DRMacIver> | Heffalump: The story with clustering multiple machines is particularly special |
| 16:58:09 | <Heffalump> | oh? |
| 16:58:11 | <Baughn> | Heffalump: I seem to recall some company once wanted to price proportional to the number of /execution units/ in the CPU |
| 16:58:23 | <jdh30> | I've heard that story before... |
| 16:58:27 | <DRMacIver> | There are two types of license. The standard and the enterprise license. |
| 16:58:31 | <Heffalump> | Baughn: why not just do it in proportion to the number of transistors x the clock rate? |
| 16:58:37 | <DRMacIver> | With the standard license you may cluster up to 4 machines for free. |
| 16:58:41 | <pejo> | Heffalump, they have some fishy stuff like charging for the amount of physical CPUs in the machine, instead of how many you actually use for example. |
| 16:58:42 | <DRMacIver> | You may not cluster more than 4 machines. |
| 16:58:48 | <jdh30> | Or the power dissipation?> |
| 16:58:49 | <Baughn> | Heffalump: Presumably because that's more or less a secret |
| 16:59:04 | <Heffalump> | don't CPU manufacturers generally advertise the number of transistors? |
| 16:59:12 | <Baughn> | Sure. To two significant digits. |
| 16:59:14 | <DRMacIver> | If you want to cluster more than 4 machines you need to buy the enterprise license for them, which costs > twice the prices of the standard license. |
| 16:59:14 | <Heffalump> | anyway, jdh30's idea is probably a good proxy (and easier to find out) |
| 16:59:17 | <jdh30> | It is a bit odd. I hadn't actually thought how we should start to impose such constraints on our own software. |
| 16:59:19 | <Heffalump> | Baughn: that would be enough. |
| 16:59:31 | <Baughn> | Heffalump: Well, probably |
| 16:59:39 | <Heffalump> | jdh30: you're not big enough to make it wortwhile, I suspect. There's a lot of overhead in doing it. |
| 16:59:41 | <Baughn> | Heffalump: Just don't ask me to run oracle on the gpu |
| 16:59:42 | <DRMacIver> | But you no longer get those four machines clustered for free. And you have to pay an additional outrageous amount for every machine you want to cluster. |
| 17:00:06 | <DRMacIver> | </outrage> |
| 17:00:08 | <jdh30> | Well, we already have customers beating down our door to release new versions of our libraries as soon as a new F# compiler is out. |
| 17:00:20 | <Heffalump> | well, licence an ARM core and you have to pay an additional amount for every single one you fab :-) |
| 17:00:26 | <jdh30> | Sooner or later, we shall no doubt start charging money for the priviledge (when everything is out of beta release). |
| 17:00:44 | <jdh30> | Is that proportional to the floor space of the fab? |
| 17:00:58 | <Heffalump> | jdh30: I think I'd be pretty annoyed (as a customer) if you charged me to give me a recompiled version of the same source. |
| 17:01:22 | <Heffalump> | but once F# is out of beta that won't really be necessary anyway |
| 17:01:28 | <jdh30> | The journals are quite bad in this context, actually. We have two customers who regularly consume more bandwidth than everyone else combined. |
| 17:01:39 | <Botje> | dammit |
| 17:01:55 | <jdh30> | There will be several incompatible releases over the next 2-3 years. |
| 17:02:00 | <jdh30> | We could charge for each. |
| 17:02:03 | <Heffalump> | jdh30: no, it's per core (with different rates for different cores) |
| 17:02:17 | <Baughn> | Heffalump: I just had a thought. There are people who charge per cpu core, regardless of whether or not they're actually being /used/? |
| 17:02:30 | <Heffalump> | Baughn: apparently Oracle do, from the conversation above |
| 17:02:38 | <Baughn> | Heffalump: I wonder how that's going to work with nanocomputers, where you might conceivably stick a couple million cores in a laptop just in case they come in handy someday |
| 17:02:51 | <Heffalump> | I think the business models might perhaps change by that time :-) |
| 17:02:51 | <DRMacIver> | I suspect they'll change the model by then. :) |
| 17:03:13 | <jdh30> | I wonder what the next model will be... |
| 17:03:14 | <Baughn> | Hey, could be just a decade. ^^; |
| 17:03:26 | <Baughn> | jdh30: Heavily DRM'd, I get the impression |
| 17:04:20 | <cjb> | all this talk of charging people for access to math is making me nauseous :) |
| 17:04:37 | <cjb> | ACTION == Linux-using hippy, or something. |
| 17:04:59 | <DRMacIver> | Charging people for access to maths seems fairly reasonable to me. |
| 17:05:04 | <Baughn> | ACTION == Hardware hippy working on self-plugging extension cords |
| 17:05:11 | <DRMacIver> | Good numerical routines are really hard to do well and efficiently. |
| 17:05:18 | <jdh30> | True. |
| 17:05:40 | <jdh30> | However, most of the numerical libraries on .NET are of extremely low quality. That was one of the reasons we went into that market. |
| 17:05:43 | <DRMacIver> | Although I certainly wouldn't say no to good free numerical libraries. |
| 17:05:58 | <cjb> | DRMacIver: It's just so far away from any reasonable utopia. You want to build something, so you go to the math store and buy some math, but only rich people can afford the best math, and blargh. |
| 17:06:04 | <u_quark> | hello, where can i find some help/documentation on happs ? |
| 17:06:15 | <jdh30> | Linux has better free numerical libraries than .NET has commercial numerical libraries but there is still huge demand for any numerical libraries on .NET. |
| 17:06:26 | <cjb> | u_quark: #happs, usually |
| 17:06:39 | <jdh30> | cjb: what is the alternative? |
| 17:06:44 | <u_quark> | cjb: no luck :P |
| 17:06:45 | <DRMacIver> | Ideally the way this would work would be some open standard for the interface and then you could choose between free or commercial implementations. |
| 17:07:02 | <DRMacIver> | But for most of such the "open standard" is the de facto fortran ones. :) |
| 17:07:10 | <Heffalump> | cjb: someone has to pay to create the math, though, otherwise it won't be created at all. |
| 17:07:11 | <cjb> | jdh30: well, having software that no-one owns, of course. I guess you want to turn my moral nausea into an economic one. |
| 17:07:14 | <jdh30> | Yes. |
| 17:07:39 | <jdh30> | cjb: how do the creators of the software feed their kids? |
| 17:07:46 | <Heffalump> | I think the present world, where open-source and proprietary code compete, works quite well. |
| 17:07:47 | <obk> | It seems profiling only creates an empty .prof file if the process is interrupted. Back to binary search of the code :-( |
| 17:07:53 | <jdh30> | cjb: or are you assuming that programmers do not breed? |
| 17:07:57 | <Heffalump> | obk: do a heap profile, those write out partial results. |
| 17:08:01 | <cjb> | jdh30: by being bartenders? :) I'm regularly unpaid for the software I write. |
| 17:08:08 | <obk> | Thanks |
| 17:08:17 | <DRMacIver> | Heffalump: I agree, but I'd like to see more standardisation across the two so it was more easy to get started and transition later. |
| 17:08:36 | <Heffalump> | DRMacIver: the question is where you draw the balance on allowing lock-in. |
| 17:08:38 | <cjb> | anyway, I think I'd favor a software tax in this case. We don't need 30 competing numerical algorithms libraries, we just need a handful of good ones. |
| 17:08:46 | <jdh30> | cjb: Sure but free software usually really sucks. You get what you pay for. That is even true of FPLs now, IMHO... |
| 17:08:50 | <Heffalump> | lock-in creates more value for commercial vendors at the expense of everyone else |
| 17:08:58 | <DRMacIver> | Indeed. It's hard to get right. |
| 17:09:03 | <Heffalump> | which is good in terms of having them produce stuff, but bad in terms of having that stuff be used efficiently |
| 17:09:43 | <jdh30> | Heffalump: That is not true. We are benefitting enormously from Microsoft's locked-in customers. |
| 17:09:51 | <Heffalump> | I think patent and copyright terms for computing stuff should be reduced massively. |
| 17:09:56 | <DRMacIver> | Heffalump: I don't think lock in is a massive problem in that regards, in that I'm talking about the case of doing well enough on the open source case and then making it easier to migrate to a closed one. |
| 17:10:08 | <Heffalump> | jdh30: in that context, you are the same commercial vendor as Microsoft. |
| 17:10:50 | <DRMacIver> | I agree that reduction of patent and copyright issues for software would be a big win. |
| 17:10:54 | <jdh30> | Heffalump: Then you are talking about lock in to an entire industry, which is silly. Nobody is any more locked in to our libraries than they are to KMail. |
| 17:10:57 | <Heffalump> | DRMacIver: oh, right. I assumed you meant the other way. |
| 17:11:22 | <Heffalump> | jdh30: no, I'm talking about lock-in to an entire subset of the industry, where industry = software development and sub-set = the M$ ecosystem |
| 17:11:31 | <DRMacIver> | Heffalump: No. I'm in favour of commercial software and libraries. What I'm not in favour of is *requiring* their use. |
| 17:11:55 | <Heffalump> | DRMacIver: right, but I thought you wanted to make it easier to migrate from commerical libraries to open-source ones, but it turned out you meant the other way round. |
| 17:12:00 | <DRMacIver> | Which is why an open standard that can be shared between commercial and open source implementations are a good thing. |
| 17:12:01 | <Heffalump> | lock-in is rather more relevant in the former case. |
| 17:12:06 | <DRMacIver> | Absolutely. |
| 17:12:15 | <Heffalump> | in any case, I entirely agree about open standards |
| 17:12:26 | <jdh30> | DRMacIver: That's fair enough but there is an enormous gap between free and commercial software. Look for free alternatives to Mathematica, for example. |
| 17:12:35 | <DRMacIver> | I know that. |
| 17:12:45 | <DRMacIver> | I'm talking about a hypothetical "How I'd like things to be" :) |
| 17:12:52 | <DRMacIver> | Particularly in the case of things like numerical libraries |
| 17:13:57 | <obk> | heffalump: You sure about the partial results? I'm getting an empty .hp file |
| 17:14:28 | <Heffalump> | obk: well, I do it all the time, so I'm pretty sure, yes :-) |
| 17:14:40 | <obk> | +RTS -h<what> ? |
| 17:14:42 | <Heffalump> | -hc |
| 17:14:51 | <Heffalump> | what GHC version are you using? |
| 17:15:04 | <obk> | 6.8.2 |
| 17:15:10 | <Heffalump> | well, -hc is what I usually use, but I've tried all the options. Not sure if I've interrupted them all, though. |
| 17:15:14 | <jdh30> | DRMacIver: How could commercial software survive without copyright? |
| 17:15:26 | <Heffalump> | I'm mostly using an early 6.9 snapshot. But I could test with 6.8.2 quickly too, one sec. |
| 17:15:29 | <obk> | You kill the program before it exits and you get a non-empty .hp file? |
| 17:15:38 | <Heffalump> | obk: I ^C it |
| 17:15:38 | <obk> | Thanks |
| 17:15:40 | <Heffalump> | not kill -9 it |
| 17:15:44 | <obk> | Me too |
| 17:15:45 | <Heffalump> | or even kill -TERM |
| 17:15:51 | <Heffalump> | obk: what platform are you on? |
| 17:15:58 | <obk> | Ubuntu hardy |
| 17:16:09 | <Heffalump> | jdh30: I don't think DRMacIver is suggesting abolishing copyright for code, just for standards (if anything) |
| 17:16:24 | <DRMacIver> | I'm definitely not in favour of abolishing copyright for code. |
| 17:16:32 | <DRMacIver> | I'm much more so about patents. |
| 17:16:35 | <Heffalump> | actually, I take that back, I can't test easily with 6.8.2. But I'll test with 6.9 on linux. |
| 17:16:51 | <obk> | Heffalump: What platform are you using? |
| 17:17:02 | <Heffalump> | the one I do it on most is Windows |
| 17:17:11 | <DRMacIver> | It's more that I'd like more openness within the commercial implementations and collaboration with open source versions. |
| 17:17:16 | <Heffalump> | but I have some profiling-compiled code lying around I'm about to try on Linux |
| 17:17:40 | <DRMacIver> | An ideal situation would be that companies contributed to open source software and sold their own value added version. (Not quite like what QT do, though that works too) |
| 17:17:55 | <Igloo> | obk: -h doesn't make a .prof file, you need -p for that |
| 17:18:11 | <jdh30> | DRMacIver: Consider our closed-source F# for Numerics product and the open source Math.NET, for example. How would you have us collaborate? |
| 17:18:12 | <Heffalump> | Igloo: obk is talking about the .hp file |
| 17:18:17 | <obk> | Igloo: I'm doing -hc and looking at the .hp file |
| 17:18:34 | <Heffalump> | obk: I just did that with 6.9.20080316 and I have a non-empty .hp file. |
| 17:18:43 | <Heffalump> | ./foo_p +RTS -hc -RTS ; wait a bit ; ^C |
| 17:18:45 | <obk> | Maybe it is a new 6.9 feature then |
| 17:18:51 | <Heffalump> | I didn't think it was. |
| 17:18:53 | <Igloo> | Fair enough, I was going by "[18:07] < obk> It seems profiling only creates an empty .prof file if the process is interrupted. Back to binary search of the code :-(" :-) |
| 17:18:56 | <Heffalump> | but Igloo can confirm. |
| 17:18:59 | <jdh30> | DRMacIver: Do you think it is possible to earn money that way? |
| 17:19:05 | <Heffalump> | Igloo: we moved on frmo that, I suggested a heap profile |
| 17:19:09 | <Heffalump> | see [18:13] |
| 17:19:15 | <Igloo> | Ah, OK. It should work in 6.8, anyway |
| 17:19:25 | <obk> | Igloo: yes, that's true, when I was using -p :-) |
| 17:19:43 | <jdh30> | DRMacIver: What happens when another open source developer improves the open source version? You can't copy it into your product so they diverge? |
| 17:20:09 | <Deewiant> | Igloo: this sounds highly platform-dependent unless there are explicit flushes in the code |
| 17:20:09 | <DRMacIver> | jdh30: Ideally the two would be interface compatible, or have a large subset that was (presumably Math.NET is C# oriented, so this isn't practical here). Sharing some subset of the implementation may be good. |
| 17:20:39 | <obk> | ACTION let it run for over a minute, buffered output should have produced _something_ I think... |
| 17:20:41 | <DRMacIver> | jdh30: And if another open source developer improves the open source version, you'd hopefully be able to integrate those improvements. |
| 17:21:13 | <Heffalump> | obk: yes, it should have |
| 17:21:21 | <DRMacIver> | But you would add value in a) Performance (you might even be able to do so more than you would if you developed it on its own) and b) Additional features (this is where the "large subset" becomes an option). |
| 17:21:28 | <DRMacIver> | As to whether it's possible to make money this way, I don't know. |
| 17:21:40 | <DRMacIver> | It might be that it's not. Or at least that it's prohibitively difficult. |
| 17:21:46 | <DRMacIver> | It would be interesting to find out. |
| 17:21:52 | <obk> | Heffalump: Did you say you have a _p at the end of the executable? I don't! |
| 17:21:59 | <jdh30> | Interesting idea. |
| 17:22:16 | <Heffalump> | obk: that's just because I name my profiling executables separately to my non-profiling ones |
| 17:22:17 | <obk> | I have Gch-Options set to -prof -auto-all and the exe does respond well to +RTS -hc, so ... |
| 17:22:20 | <obk> | Ah |
| 17:22:21 | <obk> | Ok |
| 17:22:25 | <Heffalump> | I used -o foo_p when I compiled |
| 17:22:28 | <obk> | ACTION was worried he's running the wrong exe |
| 17:22:40 | <Heffalump> | the exe wouldn't run with the RTS option if it wasn't compiled for it |
| 17:22:46 | <Heffalump> | is your code (or binary) available? |
| 17:23:20 | <obk> | Is ~1600 lines in 7 files |
| 17:23:21 | <Igloo> | obk: Definitely works here with 6.8.2 on amd64/Linux |
| 17:23:26 | <obk> | I can zip it to you if you want |
| 17:23:26 | <Heffalump> | ACTION is sleepy, and hasn't accomplished any of the stuff he meant to today. Grmph. |
| 17:23:34 | <Heffalump> | sure. |
| 17:23:39 | <obk> | Sec |
| 17:23:48 | <DRMacIver> | jdh30: Even if you offered a very large supset of the open source version in the commercial version, it would be good if one could easily migrate from the open source to the commercial one. |
| 17:23:50 | <Heffalump> | preferably mail it to ganesh@earth.li |
| 17:24:08 | <DRMacIver> | jdh30: It may even be that this is *more* profitable, because you can get people hooked on an open source library and then offer them shiny incentives to pay you. :) |
| 17:24:33 | <jdh30> | Yes. That is much closer to the shareware approach to business. I've never tried it. |
| 17:24:51 | <jdh30> | Our next major venture may well be a game... |
| 17:25:06 | <Heffalump> | I'm sure some people would be able to make money this way, and I think it's very likely that it would be fewer people than can make money now. |
| 17:25:07 | <DRMacIver> | It's different from shareware because it creates an open standard which other people are free to improve upon. |
| 17:25:55 | <DRMacIver> | Heffalump: Yes. I suspect that's true. |
| 17:26:18 | <DRMacIver> | Heffalump: But not very many people are making money on libraries anyway are they? At least compared to the application and services markets |
| 17:26:20 | <gubagem> | is there any physical example for a monad? or is it sooo abstract none exists |
| 17:26:31 | <vixey> | @instances Monad |
| 17:26:33 | <lambdabot> | ((->) r), ArrowMonad a, Cont r, ContT r m, Either e, ErrorT e m, IO, Maybe, RWS r w s, RWST r w s m, Reader r, ReaderT r m, ST s, State s, StateT s m, Writer w, WriterT w m, [] |
| 17:26:38 | <Heffalump> | DRMacIver: I wouldn't have thought so, no. But jdh30 is :-) |
| 17:26:38 | <vixey> | gubagem: there are lots of examples |
| 17:26:49 | <DRMacIver> | Heffalump: And this might well benefit the latter markets more than it does the former. |
| 17:26:49 | <opqdonut> | gubagem: all the physical metaphors (containers etc) tend to be pretty poor |
| 17:26:59 | <DRMacIver> | err |
| 17:27:02 | <DRMacIver> | more than it hurts the former |
| 17:27:03 | <cjb> | gubagem: Schroedinger's Box? :) |
| 17:27:08 | <Heffalump> | DRMacIver: well, only if a decent set of libraries still got produced. |
| 17:27:32 | <DRMacIver> | Indeed. |
| 17:27:34 | <jdh30> | Heffalump: are you Ganesh? |
| 17:27:46 | <obk> | Heffalump: ben-kiki.org/Obk.tgz |
| 17:27:48 | <DRMacIver> | I'd rather have a good set of libraries in the current system than a bad in the one I'm suggesting |
| 17:27:49 | <Heffalump> | well, that's my name, yes. |
| 17:27:55 | <jdh30> | Oh, hi. |
| 17:27:58 | <Heffalump> | as /whois should tell you :-) |
| 17:27:59 | <jdh30> | Hello again. :-) |
| 17:27:59 | <DRMacIver> | Like I say, I don't really know if this would work. But it's a nice theory. :) |
| 17:28:18 | <Heffalump> | hi :-) I assumed you would have already worked out who I am :-) |
| 17:28:22 | <jdh30> | So it does. Wonders never cease... |
| 17:28:34 | <jdh30> | No, I had no idea. I had some strange images from the name though... |
| 17:29:22 | <jdh30> | DRMacIver: the sticking point of your idea is giving away half of my work (that already earns me money) for free. |
| 17:29:49 | <Lycurgus> | sticky sticky |
| 17:29:54 | <Heffalump> | jdh30: well, it's a sticking point for you, but DRMacIver's thesis is that it would make the world a better place overall. |
| 17:29:57 | <jdh30> | Also, you cannot grow such a thing because a commercial product must reach a certain size before anyone will buy it. |
| 17:30:38 | <jdh30> | Heffalump: Sure, but impractical routes to utopia aren't very useful. |
| 17:30:40 | <DRMacIver> | jdh30: It doesn't actually need that though. For example, my idea is compatible with you not publishing a single line of code but instead providing a publicly specified API and selling an implementation of that. |
| 17:30:52 | <Lycurgus> | ACTION sees a future for jdh30 in ... |
| 17:30:55 | <Heffalump> | jdh30: we don't know if it's impractical or not, though |
| 17:30:58 | <jdh30> | Ah, ok. That is what we already do though. |
| 17:31:12 | <Heffalump> | obk: your program terminates quite fast when I run it |
| 17:31:17 | <jdh30> | Well, if it is what we already do then it is clearly practicable. :-) |
| 17:31:19 | <obk> | Sigh |
| 17:31:22 | <obk> | As it should |
| 17:31:26 | <Heffalump> | ghc -prof -auto-all --make -o obk Main.hs |
| 17:31:28 | <Lycurgus> | management (if you're not there already). |
| 17:31:28 | <Heffalump> | is how I compiled it |
| 17:31:41 | <obk> | Maybe I should upgrade to 6.9 |
| 17:31:43 | <Heffalump> | jdh30: that doesn't prove that the alternative is impractical. |
| 17:31:49 | <Heffalump> | obk: no, this is with 6.8.2 |
| 17:31:56 | <jdh30> | I'd like to try Frag again but I get "Could not find module `Graphics.UI.GLUT'". Can I install it with apt? |
| 17:32:02 | <obk> | <grrr> Must be some strange environment issue |
| 17:32:07 | <jdh30> | Heffalump: yes. |
| 17:32:10 | <DRMacIver> | jdh30: Well, sortof. I suspect it's more of a "here's our API, feel free to have a browse". I'm suggesting it should be unencumbered and vaguely standardised. |
| 17:32:19 | <Baughn> | jdh30: Yes. Something like libghc6-foo-bar-glut-dev |
| 17:32:34 | <Heffalump> | DRMacIver: but the conversation above implied that his API in F# for numerics is valuable in itself. |
| 17:33:02 | <DRMacIver> | Indeed. And I'll grant that that's a potential problem. :) |
| 17:33:20 | <jdh30> | I already have libghc6-glut-dev |
| 17:33:20 | <Heffalump> | obk: also, by interrupting it quickly with +RTS -hc -RTS, I still managed to get a partial .hp file. |
| 17:33:24 | <obk> | Hey! |
| 17:33:31 | <obk> | If I compile it like you do it works! |
| 17:33:41 | <Heffalump> | how were you compiling it? |
| 17:33:42 | <Igloo> | How were you compiling it? |
| 17:33:47 | <obk> | But if I compile it as part of a package (see the README for the flags) it does not! |
| 17:33:50 | <obk> | Aha! |
| 17:33:56 | <obk> | Must be some combination of the extensions |
| 17:34:02 | <obk> | I'll do a quick binary search on them |
| 17:34:09 | <Igloo> | Are you compiling the package with -prof? |
| 17:34:22 | <Igloo> | And -auto-all? |
| 17:34:25 | <obk> | Just that program but it does not link with the rest of the package |
| 17:34:37 | <jdh30> | So how do I compile frag? |
| 17:34:45 | <Igloo> | I didn't follow that |
| 17:35:51 | <jdh30> | Oh no, wait. I have to use "ghc-6.8.2" instead of just "ghc". Hmm, lots of warnings... |
| 17:36:17 | <Baughn> | jdh30: Hm, how many ghcs do you have installed? |
| 17:36:28 | <Baughn> | jdh30: It might be more convenient to use cabal (the binary) to install it |
| 17:37:11 | <jdh30> | 5 different names for 3 versions. I don't need any though, so I can just remove them. |
| 17:37:33 | <obk> | Ok, now *this* is strange. If I compile it through runhaskell Setup.hs, it goes into the loop; if I compile it with --make, it works fine. |
| 17:37:47 | <obk> | How to I see _exactly_ how the cabal is compiling it? |
| 17:37:50 | <Heffalump> | -v |
| 17:38:03 | <obk> | ACTION always felt Cabal not using make is a mistake :-) |
| 17:38:21 | <mauke> | I have make use cabal |
| 17:38:23 | <Heffalump> | I tend to agree |
| 17:38:27 | <Baughn> | obk: make isn't flexible enough. Now, not building them into each other mmight be a mistake |
| 17:38:30 | <mauke> | EGRAMMAR |
| 17:38:34 | <Heffalump> | though it's tricky because make isn't cross-platform |
| 17:38:52 | <Baughn> | Hang on. make, or --make? |
| 17:39:02 | <Deewiant> | --make. |
| 17:39:03 | <Heffalump> | make. |
| 17:39:19 | <Deewiant> | it started with --make. :-) |
| 17:39:26 | <Heffalump> | it seems there are cross-purposes going on here :-) |
| 17:39:28 | <dmwit> | runhaskell doesn't compile it. |
| 17:39:28 | <obk> | Baughn: there's gnu make, and jam, cake, bake, rake, cook, to name a few off the top of my head. We could easily write hake if we wanted to (like rake). |
| 17:39:29 | <Baughn> | Ow my head -_- |
| 17:39:40 | <Heffalump> | dmwit: runhaskell Setup.lhs build does |
| 17:39:48 | <dmwit> | Okay, yes. |
| 17:39:52 | <Baughn> | obk: The cake is a lie. Might as well use fake |
| 17:39:57 | <Heffalump> | I want cake now. |
| 17:40:02 | <obk> | Anyway. I got the list of commands cabal is using. I'll do a binary search to find out what is the offending flag(s) |
| 17:40:20 | <alexander> | insane how this nick wasn't taken :) |
| 17:40:32 | <obk> | alexander: They die young :-) |
| 17:41:13 | <HairyDude> | @hoogle Monoid a => Bool -> a -> a |
| 17:41:14 | <lambdabot> | GHC.Exts.breakpointCond :: Bool -> a -> a |
| 17:41:14 | <lambdabot> | Control.Exception.assert :: Bool -> a -> a |
| 17:41:52 | <dmwit> | :t let ensure p x = guard p >> return (p x) in ensure |
| 17:42:04 | <Deewiant> | @bot |
| 17:42:05 | <lambdabot> | :) |
| 17:42:06 | <dmwit> | *poke* |
| 17:42:07 | <lambdabot> | thread killed |
| 17:42:11 | <dmwit> | :t let ensure p x = guard p >> return (p x) in ensure |
| 17:42:12 | <Deewiant> | @ty let ensure p x = guard p >> return (p x) in ensure |
| 17:42:16 | <mauke> | dmwit: looks like a type error |
| 17:42:19 | <HairyDude> | :t ensure b x = if b then x else mempty |
| 17:42:27 | <lambdabot> | thread killed |
| 17:42:27 | <lambdabot> | thread killed |
| 17:42:31 | <Deewiant> | > 1+1 |
| 17:42:31 | <HairyDude> | dmwit: that unnecessarily depends on Monad |
| 17:42:34 | <pastorn> | @type guard |
| 17:42:34 | <lambdabot> | thread killed |
| 17:42:38 | <pastorn> | @type guard |
| 17:42:40 | <HairyDude> | oh dear, lambda bot is feeling ill again :( |
| 17:42:43 | <dmwit> | mauke: YOu're right. |
| 17:42:46 | <lambdabot> | thread killed |
| 17:42:49 | <lambdabot> | forall (m :: * -> *). (MonadPlus m) => Bool -> m () |
| 17:42:51 | <lambdabot> | forall (m :: * -> *). (MonadPlus m) => Bool -> m () |
| 17:42:55 | <Deewiant> | > 2+2 |
| 17:42:56 | <lambdabot> | 4 |
| 17:42:58 | <dmwit> | :t let ensure p x = guard (p x) >> return x in ensure |
| 17:43:00 | <lambdabot> | forall b (m :: * -> *). (MonadPlus m) => (b -> Bool) -> b -> m b |
| 17:43:03 | <HairyDude> | :t ensure b x = if b then x else mempty |
| 17:43:04 | <pastorn> | @type guard |
| 17:43:04 | <lambdabot> | parse error on input `=' |
| 17:43:06 | <lambdabot> | forall (m :: * -> *). (MonadPlus m) => Bool -> m () |
| 17:43:14 | <HairyDude> | :t let ensure b x = if b then x else mempty in ensure |
| 17:43:16 | <lambdabot> | forall a. (Monoid a) => Bool -> a -> a |
| 17:43:33 | <HairyDude> | funny that that isn't in Data.Monoid already, it seems useful |
| 17:43:49 | <dmwit> | HairyDude: I know it depends on MonadPlus, I just want that ensure more often than I want your one. =) |
| 17:44:45 | <Heffalump> | I don't really understand why that should be called 'ensure' |
| 17:44:46 | <HairyDude> | dmwit: {-# LANGUAGE FlexibleContexts, OverlappingInstances #-} instance MonadPlus m => Monoid (m a) where { mempty = mzero; mappend = mplus } |
| 17:45:06 | <dmwit> | sure |
| 17:45:17 | <dmwit> | Heffalump: Something like this: |
| 17:45:34 | <dmwit> | Heffalump: [1..10] >>= ensure even |
| 17:45:51 | <dmwit> | > let ensure p x = guard (p x) >> return x in [1..10] >>= ensure even |
| 17:45:52 | <lambdabot> | [2,4,6,8,10] |
| 17:46:20 | <mar77a> | :t ensure |
| 17:46:21 | <lambdabot> | Not in scope: `ensure' |
| 17:46:25 | <mar77a> | doh |
| 17:46:31 | <jdh30> | bfn |
| 17:46:35 | <Heffalump> | I understand the MonadPlus one, but not the Monoid one. |
| 17:46:37 | <dmwit> | (b -> Bool) -> b -> monadPlus b |
| 17:46:59 | <HairyDude> | Heffalump: the function, or just its name? I'm not attached to that name, in fact I called it something else |
| 17:47:04 | <Heffalump> | it's name |
| 17:47:10 | <Heffalump> | s/it's/its/ # gah |
| 17:53:34 | <HairyDude> | ACTION wonders why guard has to use m () instead of m a |
| 17:53:59 | <vixey> | @src guard |
| 17:53:59 | <lambdabot> | guard True = return () |
| 17:53:59 | <lambdabot> | guard False = mzero |
| 17:54:02 | <vixey> | that's why |
| 17:54:25 | <HairyDude> | oh wait, that's not the function I was thinking of |
| 17:54:26 | <obk> | Obvious in retrospect |
| 17:54:32 | <HairyDude> | I mean when |
| 17:54:34 | <obk> | Bug was introduced by the -O compile flag |
| 17:54:36 | <HairyDude> | @src when |
| 17:54:37 | <lambdabot> | when p s = if p then s else return () |
| 17:54:43 | <obk> | Haffelump: Can you verify? |
| 17:54:44 | <HairyDude> | :t when |
| 17:54:45 | <lambdabot> | forall (m :: * -> *). (Monad m) => Bool -> m () -> m () |
| 17:55:43 | <dmwit> | when doesn't require MonadPlus |
| 17:56:34 | <obk> | Heffalump: Can you test whether -O also breaks this program on 6.9 ? |
| 17:57:05 | <Vq^> | i can't grok this memoization with recursion from the haskell wiki |
| 17:57:20 | <vixey> | Vq^: we could look at fibs if you like? |
| 17:57:25 | <HairyDude> | ah, so it doesn't |
| 17:57:44 | <Heffalump> | obk: confirmed that it hangs on 6.8.2 |
| 17:57:58 | <Vq^> | whats so different between "fib n = map fib' [0..] !! n" and "fib = (map fib' [0..] !!)" |
| 17:58:09 | <obk> | relief! my machine is not haunted by gremlins! :-) |
| 17:58:21 | <obk> | Heffalump: In 6.9 as well? |
| 17:58:24 | <Heffalump> | it also doesn't interrupt properly, which probably explains the empty .hp |
| 17:58:38 | <Heffalump> | oh, though I have a non-empty .hp, actually |
| 17:58:53 | <obk> | Well, either way, this seems worthy of a bug report. |
| 17:59:03 | <obk> | Though less so if it was fixed on 6.9 |
| 17:59:10 | <Heffalump> | yeah, just about to try that |
| 17:59:19 | <Vq^> | vixey: fibs? |
| 18:00:08 | <Heffalump> | it segfaults! |
| 18:00:21 | <vixey> | Vq^: it's a good example because the recursion blows up really fast |
| 18:00:27 | <obk> | Ha! |
| 18:00:30 | <obk> | Even better |
| 18:00:37 | <obk> | Ok, I'm entering a bug report on this |
| 18:00:47 | <vixey> | > let fib 0 = 0 ; fib 1 = 1 ; fib n = fib (n-2) + fib (n-1) in fib 3 |
| 18:00:48 | <obk> | Heffalump: many thanks for the help! |
| 18:00:48 | <lambdabot> | 2 |
| 18:00:50 | <ttt--> | @src when |
| 18:00:51 | <lambdabot> | when p s = if p then s else return () |
| 18:00:52 | <vixey> | > let fib 0 = 0 ; fib 1 = 1 ; fib n = fib (n-2) + fib (n-1) in fib 300 |
| 18:00:55 | <Vq^> | vixey: well, i understand memoization and every fibonacci example i have seen so far |
| 18:01:02 | <lambdabot> | Exception: Time limit exceeded |
| 18:01:08 | <obk> | Now how do I tell cabal not to use -O ... hmmm... looking up |
| 18:01:34 | <vixey> | > let fib 0 = 0 ; fib 1 = 1 ; fib n = fib' (n-2) + fib' (n-1) ; fib' n = fibs!!n ; fibs = map fib [0..] in fib 300 |
| 18:01:35 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:02:05 | <vixey> | Vq^: so is it clear why this version memoized? |
| 18:02:14 | <Vq^> | vixey: yes, very clear |
| 18:02:23 | <Heffalump> | obk: -O0 as an explicit option |
| 18:02:29 | <Vq^> | vixey: thought i like the zipWith trick better ;) |
| 18:02:31 | <obk> | Thanks! |
| 18:02:37 | <Heffalump> | at a guess, anyway |
| 18:02:45 | <Heffalump> | it would be silly if that didn't work |
| 18:02:53 | <vixey> | Vq^: what's that? |
| 18:03:04 | <Saizan> | obk: configure with --disable-optimization |
| 18:03:12 | <vixey> | Vq^: changing the entire algorithm just to memo? |
| 18:03:13 | <Vq^> | > let fibs = 0 : 1 : zipWith (+) fibs (tail fibs) in fibs !! 300 |
| 18:03:15 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:03:18 | <obk> | Saizan: But then my users will suffer |
| 18:03:21 | <vixey> | yeah not so keen on that |
| 18:03:26 | <Deewiant> | > let fibs = fix ((0:).scanl (+) 1) in fibs !! 300 |
| 18:03:27 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:03:40 | <Baughn> | obk: You've tracked the loop to the /optimizer/? |
| 18:04:02 | <obk> | Baughn: Yes!!! |
| 18:04:02 | <Heffalump> | Baughn: seems so. |
| 18:04:17 | <obk> | Should have been the 1st thing I tried <sheepish> |
| 18:04:34 | <mauke> | :t ((. flip (:)) . (flip ($!))) |
| 18:04:35 | <lambdabot> | forall a. a -> [a] -> [a] |
| 18:04:38 | <Baughn> | obk: Then. It might be a bit hard, but it would be a very good thing to figure out exactly what causes it - the optimizer should never, ever do that. |
| 18:04:48 | <Vq^> | my problem is when there is no clear list of memoized values |
| 18:04:49 | <Deewiant> | @unpl ((. flip (:)) . (flip ($!))) |
| 18:04:50 | <lambdabot> | (\ j m -> (\ c -> (:) c m) $! j) |
| 18:04:54 | <Heffalump> | we really could do with a proper reducer for Haskell code |
| 18:05:05 | <vixey> | Heffalump: what would it do? |
| 18:05:14 | <vixey> | like an evaluator but step by step? |
| 18:05:15 | <Heffalump> | cut down test cases like this |
| 18:05:22 | <vixey> | huh |
| 18:05:25 | <Vq^> | http://haskell.org/haskellwiki/Memoization#Memoization_with_recursion |
| 18:05:29 | <lambdabot> | Title: Memoization - HaskellWiki, http://tinyurl.com/65yh9u |
| 18:05:32 | <Heffalump> | hangon, I'm trying to find the C utility I'm thinking of |
| 18:05:38 | <obk> | Baughn: I am submitting a bug report with the program |
| 18:05:54 | <DRMacIver> | Heffalump: You mean delta? |
| 18:05:59 | <Heffalump> | DRMacIver: yes, I do. Thanks! |
| 18:06:04 | <Vq^> | im trying to understand how memoized_fib evaluates |
| 18:06:04 | <DRMacIver> | No problem |
| 18:06:08 | <mauke> | > let fs = 0 : 1 : zipWith (+) fs (tail fs) in fs !! 10000 |
| 18:06:10 | <lambdabot> | 3364476487643178326662161200510754331030214846068006390656476997468008144216... |
| 18:06:14 | <mauke> | > let fs = 0 : 1 : zipWith (+) fs (tail fs) in fs !! 100000 |
| 18:06:14 | <vixey> | Vq^: That's exactly the same as my example which you said you understood ... |
| 18:06:16 | <lambdabot> | out of memory (requested 1048576 bytes) |
| 18:06:22 | <Heffalump> | if we had an unlayout utility, we could probably just use delta. |
| 18:06:56 | <Vq^> | vixey: except you defined fibs |
| 18:07:01 | <DRMacIver> | unlayout doesn't seem like it should be hard to write if you have a parser and pretty printer for Haskell already |
| 18:07:03 | <vixey> | Vq^: syntax |
| 18:07:05 | <gubagem> | @hoogle !! |
| 18:07:09 | <Heffalump> | agreed. |
| 18:07:12 | <lambdabot> | Prelude.(!!) :: [a] -> Int -> a |
| 18:07:12 | <lambdabot> | Data.List.(!!) :: [a] -> Int -> a |
| 18:07:17 | <Heffalump> | We also need a hsallinone for GHC Haskell. |
| 18:07:23 | <DRMacIver> | A what? |
| 18:07:32 | <Heffalump> | merges multiple modules into one |
| 18:07:33 | <Vq^> | vixey: i guess i don't see that jump :/ |
| 18:07:35 | <DRMacIver> | Oh, right. |
| 18:07:43 | <Deewiant> | vixey: why doesn't memoized_fib there evaluate the map fib [0..] on each call? |
| 18:07:44 | <vixey> | Vq^: there is no jump |
| 18:07:49 | <DRMacIver> | Does delta really need them all in one file? |
| 18:07:56 | <vixey> | > let fib 0 = 0 ; fib 1 = 1 ; fib n = fib' (n-2) + fib' (n-1) ; fib' n = fibs!!n ; fibs = map fib [0..] in fib 300 |
| 18:07:57 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:08:00 | <Vq^> | vixey: then i guess im just plain confused... |
| 18:08:03 | <Heffalump> | no, there's multidelta (IIRC) which doesn't. But I think it's much harder to operate. |
| 18:08:08 | <DRMacIver> | Ah |
| 18:08:14 | <Heffalump> | and it's nice to have your test case all in one file if at all possible |
| 18:08:43 | <obk> | Ticket #2327 if anyone is interested - the -O flag producing faulty code |
| 18:09:21 | <Vq^> | hmm, i guess it's the body of the function/value that is memoized_fib that gets memoized |
| 18:09:24 | <Deewiant> | > let fib 0 = 0 ; fib 1 = 1 ; fib n = fib' (n-2) + fib' (n-1) ; fib' n = map fib [0..] !!n in fib 300 |
| 18:09:25 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:09:26 | <DRMacIver> | Heffalump: True |
| 18:09:36 | <Deewiant> | vixey: that one runs much slower for me in GHCi |
| 18:09:51 | <DRMacIver> | Something like this? http://www.cs.utah.edu/~hal/HAllInOne/index.html |
| 18:09:52 | <lambdabot> | Title: Haskell All-In-One |
| 18:10:08 | <DRMacIver> | Oh, it only handles H98 |
| 18:10:09 | <Heffalump> | DRMacIver: yes, precisely that. |
| 18:10:28 | <DRMacIver> | Oh, sorry |
| 18:10:33 | <DRMacIver> | I totally misread your comment |
| 18:10:44 | <Heffalump> | I got the name slightly wrong (HSAllInOne verses HAllInOne) |
| 18:11:33 | <DRMacIver> | I parsed what you said as "We need this tool" rather than "We need this tool to support GHC's dialect of Haskell" |
| 18:11:41 | <DRMacIver> | ACTION fails. :) |
| 18:11:51 | <Heffalump> | we need such a tool that supports GHC Haskell |
| 18:12:01 | <Heffalump> | whether it's that tool update or a new one, I don't care |
| 18:13:10 | <Vq^> | vixey: i guess you are completely right, my problem is only about syntax |
| 18:14:20 | <Vq^> | it's the big difference between "f = (fs !!)" and "f x = fs !! x" that i seem to be somewhat confused by |
| 18:15:33 | <hpaste> | Orchid pasted "Achievement cat... is pround of self" at http://hpaste.org/8022 |
| 18:16:53 | <ziman> | what is the best way to parse two kinds of blocks, one beginning with "Frame ", the other with "FrameMatrix", using Parsec? do i have to factor the grammar or is there a friendlier way? :) |
| 18:17:03 | <chessguy> | @pl \s -> u s >>= u |
| 18:17:03 | <lambdabot> | (u =<<) . u |
| 18:17:22 | <mauke> | @pl \u -> u s >>= u |
| 18:17:22 | <lambdabot> | (>>=) =<< ($ s) |
| 18:17:27 | <mauke> | haha |
| 18:18:17 | <chessguy> | @pl \u s -> u s >.>= u |
| 18:18:17 | <lambdabot> | flip =<< ((>.>=) .) |
| 18:18:25 | <DRMacIver> | Hm. Is there any way to tell ghc to recompile all its libraries from source? |
| 18:18:33 | <chessguy> | @pl \s u -> u s >>= u |
| 18:18:33 | <lambdabot> | join . ((>>=) .) . flip id |
| 18:18:40 | <Heffalump> | I don't think it even knows where the source is |
| 18:18:53 | <DRMacIver> | Ah well |
| 18:19:03 | <DRMacIver> | I suspect it's time to reinstall ghc. Again. |
| 18:19:07 | <Heffalump> | why? |
| 18:19:16 | <Deewiant> | @src (>=>) |
| 18:19:17 | <lambdabot> | Source not found. You speak an infinite deal of nothing |
| 18:19:18 | <Dzlk> | ziman: for what value of "best"? |
| 18:19:21 | <Deewiant> | chessguy: (>=>) |
| 18:19:29 | <Deewiant> | @ty (>=>) |
| 18:19:30 | <DRMacIver> | Because I didn't reinstall after I last broke it with that pretty printers bug. |
| 18:19:31 | <lambdabot> | forall a (m :: * -> *) b c. (Monad m) => (a -> m b) -> (b -> m c) -> a -> m c |
| 18:19:48 | <DRMacIver> | I just rebuilt some of the modules that depended on it |
| 18:20:08 | <DRMacIver> | And now I'm finding I can't use the Language.Haskell stuff which dependended on that and can't figure out where to recompile them from. |
| 18:20:32 | <Toxaris_> | ziman: something like (keyword s = try $ string s >> whitespace), and then (keyword "FrameMatrix" >> ...) <|> (keyword "Frame" >> ...) should work |
| 18:20:37 | <Heffalump> | ah |
| 18:22:14 | <Toxaris_> | ziman: if you make sure that (keyword "Frame") does not accept "FrameMatrix", you're on the safe side. The try in keyword enables local backtracking, to allow different keywords to begin with the same prefix |
| 18:22:51 | <gpds> | how is an int different from an integer? |
| 18:23:03 | <Heffalump> | smaller range |
| 18:23:05 | <Heffalump> | integer is unbounded |
| 18:23:16 | <gpds> | whats the range? |
| 18:23:22 | <ziman> | Toxaris_, i see, thanks. I thought of `try'ing whole blocks but `try'ing the keyword is clearly better :) |
| 18:23:28 | <mauke> | > [minBound, maxBound] :: [Int] |
| 18:23:29 | <lambdabot> | [-2147483648,2147483647] |
| 18:23:40 | <gpds> | thanks! |
| 18:23:48 | <DRMacIver> | Technically the range is unspecified... |
| 18:23:50 | <Heffalump> | standard says 29 bits minimum, GHC uses machine words |
| 18:24:02 | <Toxaris_> | ziman: yeah, that's a general design pattern with Parsec: use try on the lexer level, but try :) to avoid it on the parser level |
| 18:24:03 | <DRMacIver> | At least specified to be within a certain bound |
| 18:24:15 | <Toxaris_> | ziman: with lexer and parser levels not exactly seperate :) |
| 18:25:26 | <ziman> | hm, good point |
| 18:25:41 | <chessguy> | Deewiant: is that in the libraries somewhere? |
| 18:25:47 | <chessguy> | @hoogle (>=>) |
| 18:25:47 | <lambdabot> | Control.Monad.(>=>) :: Monad m => (a -> m b) -> (b -> m c) -> a -> m c |
| 18:26:53 | <hpaste> | vicky pasted "fib memo" at http://hpaste.org/8023 |
| 18:27:03 | <chessguy> | guess that answers that question :) |
| 18:27:06 | <vixey> | Vq^ & Deewiant |
| 18:27:59 | <DRMacIver> | Heffalump: Well, I was right about it being ridiculously easy to implement NoLayout. Took all of four lines to throw together with Language.Haskell. :) |
| 18:28:07 | <DRMacIver> | (Well, four lines plus imports) |
| 18:28:24 | <mauke> | .oO( import XMonad.Layout.NoLayout ) |
| 18:28:43 | <DRMacIver> | Sorry, unlayout |
| 18:28:49 | <hpaste> | DRMacIver pasted "unlayout" at http://hpaste.org/8024 |
| 18:29:42 | <Deewiant> | vixey: how about fib2 such that fibs is written inline, i.e. fib3' n = map fib3 [0..] !! n |
| 18:29:44 | <Heffalump> | DRMacIver: does it work on GHC Haskell? I thought Language.Haskell was H98 |
| 18:29:53 | <Heffalump> | not that it's not a good thing. |
| 18:29:57 | <vixey> | Deewiant: please paste it with times |
| 18:31:36 | <DRMacIver> | Heffalump: I was under the impression that the Language.Haskell module provided with ghc used ghc's parser |
| 18:31:38 | <chessguy> | @seen conal |
| 18:31:39 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 18:31:52 | <DRMacIver> | Heffalump: Again, I could be totally wrong |
| 18:31:59 | <Heffalump> | I didn't think it had syntactic elements for non-H98. I also could be wrong. |
| 18:32:01 | <mauke> | preflex: seen conal |
| 18:32:01 | <preflex> | conal was last seen on #haskell 3 hours, 21 minutes and 47 seconds ago, saying: sjanssen: thx! |
| 18:32:12 | <ziman> | @pl \x -> whitespace >> return x |
| 18:32:13 | <lambdabot> | (whitespace >>) . return |
| 18:32:33 | <gpds> | preflex: seen jdh30 |
| 18:32:33 | <preflex> | jdh30 was last seen on #haskell 46 minutes and 1 second ago, saying: bfn |
| 18:32:38 | <Heffalump> | http://www.cs.chalmers.se/~d00nibro/haskell-src-exts/ |
| 18:32:39 | <lambdabot> | Title: haskell-src-exts: Haskell-Source with Extensions |
| 18:32:40 | <dmwit> | :t \x -> liftM (const x) whitespace |
| 18:32:42 | <lambdabot> | Not in scope: `whitespace' |
| 18:32:58 | <dmwit> | ziman: flip liftM whitespace . const |
| 18:33:07 | <gubagem> | thats fib memo code looks wicked simple |
| 18:33:07 | <dmwit> | Is even less readable. ;-) |
| 18:33:18 | <ziman> | dmwit, :D |
| 18:33:38 | <DRMacIver> | Heffalump: Hm. Just tried it, you're right |
| 18:33:50 | <hpaste> | Deewiant annotated "fib memo" with "inlining fibs" at http://hpaste.org/8023#a1 |
| 18:34:05 | <Deewiant> | vixey: as I thought, it's the slowest of all four |
| 18:34:09 | <Heffalump> | haskell-src-exts is the way to go, I suspect |
| 18:34:25 | <vixey> | Deewiant: I couldn't have predicted that |
| 18:34:36 | <BONUS> | @src ap |
| 18:34:37 | <lambdabot> | ap = liftM2 id |
| 18:34:37 | <Heffalump> | either that or ghc-api |
| 18:34:58 | <Deewiant> | vixey: it's doing the map fib3 [0..] for each call to fib3', nothing is memoized |
| 18:35:03 | <DRMacIver> | ACTION is slightly perplexed that GHC bundles a parser that doesn't handle GHC extensions. |
| 18:35:04 | <vixey> | Deewiant: I thought it would be equivalent to fib2 actually |
| 18:35:07 | <DRMacIver> | Oh welll |
| 18:35:09 | <vixey> | Deewiant: but it makes sense |
| 18:35:15 | <vixey> | in retrospect |
| 18:35:36 | <Vq^> | > let fib = (map fib' [0..] !!); fib' 0 = 0; fib' 1 = 1; fib' n = fib (n-2) + fib (n-1) in fib 300 |
| 18:35:38 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:35:51 | <Deewiant> | vixey: what I don't get is why the same doesn't happen with memoized_fib |
| 18:36:05 | <Vq^> | > let fib n = map fib' [0..] !! n; fib' 0 = 0; fib' 1 = 1; fib' n = fib (n-2) + fib (n-1) in fib 300 |
| 18:36:07 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 18:36:11 | <vixey> | have you timed memoized_fibs? |
| 18:36:17 | <vixey> | (which of my examples is it equivalent to?) |
| 18:36:23 | <Deewiant> | has the speed of fib2 |
| 18:36:29 | <vixey> | right |
| 18:36:35 | <vixey> | so it's the same code |
| 18:36:43 | <vixey> | just written in a silly way |
| 18:36:52 | <vixey> | (I think we could impove the wiki article) |
| 18:36:55 | <chessguy> | @type iterateM |
| 18:36:57 | <lambdabot> | Not in scope: `iterateM' |
| 18:37:02 | <jleedev> | > let fibs = 1 : scanl (+) 1 fibs in fibs !! 300 |
| 18:37:03 | <lambdabot> | 359579325206583560961765665172189099052367214309267232255589801 |
| 18:37:06 | <chessguy> | @hoogle iterateM |
| 18:37:06 | <lambdabot> | No matches found |
| 18:37:17 | <Vq^> | that last example i pasted doesn't terminate within a minute |
| 18:37:19 | <chessguy> | @type iterate |
| 18:37:20 | <lambdabot> | forall a. (a -> a) -> a -> [a] |
| 18:37:42 | <Vq^> | lambdabot seems to solve it thought :/ |
| 18:37:49 | <Deewiant> | vixey: but it looks like it should have the speed of fib3 :-/ |
| 18:37:58 | <DRMacIver> | Hm. Where can I find the ghc api? |
| 18:38:21 | <DRMacIver> | Ah, never mind |
| 18:39:02 | <Deewiant> | vixey: :-OOOO |
| 18:39:07 | <chessguy> | @hoogle (a -> m a) -> a -> [a] |
| 18:39:07 | <Deewiant> | vixey: making it pointy slows it down to fib3 speed |
| 18:39:07 | <lambdabot> | Prelude.iterate :: (a -> a) -> a -> [a] |
| 18:39:07 | <lambdabot> | Data.List.iterate :: (a -> a) -> a -> [a] |
| 18:39:07 | <lambdabot> | Prelude.scanl :: (a -> b -> a) -> a -> [b] -> [a] |
| 18:39:17 | <chessguy> | :hoogle+ |
| 18:39:22 | <Heffalump> | DRMacIver: it bundles a standard library |
| 18:39:27 | <chessguy> | @hoogle+ |
| 18:39:27 | <lambdabot> | Data.List.scanl :: (a -> b -> a) -> a -> [b] -> [a] |
| 18:39:27 | <lambdabot> | Prelude.scanr :: (a -> b -> b) -> b -> [a] -> [b] |
| 18:39:27 | <lambdabot> | Data.List.scanr :: (a -> b -> b) -> b -> [a] -> [b] |
| 18:39:51 | <Heffalump> | if it produced a datatype that included constructors for non-H98 stuff, that standard library wouldn't be compatible across implementations |
| 18:39:51 | <vixey> | Deewiant: at least I don't think that these 3 typed of memoization (none, one time, every time) can be written simpler |
| 18:40:26 | <chessguy> | @hoogle (a -> Maybe a) -> a -> [a] |
| 18:40:27 | <lambdabot> | No matches, try a more general search |
| 18:40:50 | <Vq^> | vixey: did you see my last fib? |
| 18:41:23 | <adekoba> | is there a variable in ghci that stores the last answer? |
| 18:41:35 | <mauke> | it |
| 18:41:44 | <adekoba> | <3 |
| 18:41:45 | <adekoba> | thanks |
| 18:42:00 | <tusho> | what are the monad laws again? |
| 18:42:04 | <hpaste> | Deewiant annotated "fib memo" with "pointless vs. pointy" at http://hpaste.org/8023#a2 |
| 18:42:07 | <tusho> | a >>= return === a |
| 18:42:10 | <tusho> | what else? |
| 18:42:11 | <Vq^> | vixey: and if you did do you know why lambdabot seems to optimize it to "do memoization"? |
| 18:42:12 | <DRMacIver> | Heffalump: I'd sortof expect that to be moved out to hackage with the library reorg if it wasn't actually part of ghc. |
| 18:42:16 | <DRMacIver> | But I guess not. |
| 18:42:25 | <chessguy> | @type \f x -> takeWhile isJust $ iterate (\x -> x >>= f) x |
| 18:42:25 | <lambdabot> | forall a. (a -> Maybe a) -> Maybe a -> [Maybe a] |
| 18:42:30 | <Deewiant> | vixey: see paste, that is weird IMO O_o |
| 18:42:36 | <mauke> | @wiki Monad_laws |
| 18:42:36 | <lambdabot> | http://www.haskell.org/haskellwiki/Monad_laws |
| 18:42:49 | <chessguy> | @pl \x -> x >>= f |
| 18:42:50 | <lambdabot> | (f =<<) |
| 18:43:00 | <Deewiant> | or (>>= f) :-P |
| 18:43:20 | <chessguy> | @pl \f x -> takeWhile isJust $ iterate (>>= f) x |
| 18:43:21 | <lambdabot> | (takeWhile isJust .) . iterate . (=<<) |
| 18:43:46 | <chessguy> | @type \f x -> takeWhile isJust $ iterate (>>= f) x |
| 18:43:47 | <lambdabot> | forall a. (a -> Maybe a) -> Maybe a -> [Maybe a] |
| 18:43:57 | <Vq^> | Deewiant: did you see lambdabots result from your fib5_ ? |
| 18:44:08 | <chessguy> | @hoogle [Maybe a] -> a |
| 18:44:09 | <lambdabot> | No matches, try a more general search |
| 18:44:18 | <chessguy> | @hoogle [Maybe a] -> [a] |
| 18:44:18 | <lambdabot> | Data.Maybe.catMaybes :: [Maybe a] -> [a] |
| 18:45:28 | <Deewiant> | Vq^: yes, can't explain it |
| 18:45:38 | <bd_> | @src catMaybes |
| 18:45:38 | <lambdabot> | catMaybes ls = [x | Just x <- ls] |
| 18:45:39 | <Deewiant> | Vq^: I'm not sure, perhaps lambdabot compiles the code? |
| 18:45:52 | <bd_> | there needs to be a maybeToMonadPlus :| |
| 18:46:06 | <Vq^> | it seems that lambdabots compiler sees that the right hand side of !! isn't affected by it's arguments |
| 18:46:19 | <Vq^> | er, left hand side |
| 18:46:51 | <hpaste> | vicky annotated "fib memo" with "clue" at http://hpaste.org/8023#a3 |
| 18:47:32 | <vixey> | Vq^: no I didn't se it |
| 18:47:35 | <Deewiant> | O_o, why does that happen |
| 18:47:44 | <vixey> | monomorphism |
| 18:47:57 | <gpds> | @type zipWith |
| 18:47:59 | <lambdabot> | forall a b c. (a -> b -> c) -> [a] -> [b] -> [c] |
| 18:48:01 | <Deewiant> | monomorphism restriction speeds up programs, right |
| 18:48:11 | <vixey> | well it's about types |
| 18:48:21 | <bd_> | Deewiant: depends |
| 18:48:23 | <vixey> | speed up is a possible consequence |
| 18:48:39 | <bd_> | Deewiant: the goal is to avoid situations where an expression is unexpectedly evaluated twice, with two different types |
| 18:48:40 | <Deewiant> | sure |
| 18:48:43 | <sclv_> | any folks familiar with DPH around? |
| 18:48:54 | <bd_> | by forcing you to explicitly annotate when you want that to happen |
| 18:48:58 | <sclv_> | The parallels with *lisp are sort of striking me lately. |
| 18:49:05 | <Deewiant> | bd_: it's just that in this case it unexpectedly causes something to be evaluated only once instead of N times :-) |
| 18:49:17 | <sclv_> | Was wondering how much influence there was (haven't trawled through all the papers yet) |
| 18:49:32 | <dons> | sclv_: very little, afaik |
| 18:49:42 | <dons> | it came out of work on nested data paralellism in the early 90s |
| 18:49:43 | <bd_> | Deewiant: oO |
| 18:50:11 | <dons> | sclv_: based on Nesl |
| 18:50:19 | <sclv_> | the distribution law of the alpha operator in *lisp is pretty cool |
| 18:50:22 | <Vq^> | the types may not be the cause thought |
| 18:50:40 | <dons> | http://citeseer.ist.psu.edu/blelloch90nesl.html |
| 18:50:42 | <lambdabot> | Title: Nesl: A Nested Data-Parallel Language - Blelloch (ResearchIndex) |
| 18:50:52 | <dons> | "Nesl, a strongly-typed, applicative, data-parallel language." |
| 18:50:57 | <bd_> | Deewiant: when you bind fibs at the toplevel (in fib2 example), GHC keeps it around until the program terminates |
| 18:50:58 | <vixey> | hi dons! |
| 18:51:17 | <Deewiant> | bd_: yep, but I'm looking only at fib5 and fib5_ |
| 18:51:38 | <vixey> | I tried to show that with fib2 vs fib3 |
| 18:51:49 | <vixey> | (specifically timing them twice) |
| 18:52:05 | <dons> | and the ubiquitous reddit link http://reddit.com/info/6lmsz/comments/ |
| 18:52:25 | <vixey> | I guess not :/ |
| 18:52:42 | <halberd> | where can I find an algorithm or heuristic for representing a graph that is not planar, but that would be planar if a few edges were removed? |
| 18:52:50 | <Vq^> | you can force the type of fib5 to Num a => Int -> a without any large difference in performance |
| 18:52:52 | <bd_> | Deewiant: hmm... I guess GHC bound (map fib5' [0..] !!) at the toplevel, thus keeping the (map fib5' [0..]) around too? |
| 18:53:10 | <halberd> | that is I want an algorithm that will take a non-planar graph and return a small set of edges that can be removed from the graph to make it planar |
| 18:53:28 | <Deewiant> | bd_: this is GHCi, I wouldn't expect it do that kind of a transformation |
| 18:53:50 | <bd_> | Deewiant: it might. |
| 18:53:55 | <bd_> | It's not actually a transformation |
| 18:53:57 | <vixey> | isn't ghci the same as ghc? |
| 18:54:10 | <Deewiant> | I don't know, is it? |
| 18:54:15 | <bd_> | vixey: It optimizes less, and uses a bytecode VM rather than a native code generator |
| 18:54:27 | <bd_> | the libraries are the same though |
| 18:54:35 | <bd_> | and the RTS |
| 18:54:36 | <Vq^> | well, lambdabot transforms f n = fs !! n to f = (fs !!) causing it to do memoization |
| 18:54:39 | <Deewiant> | bd_: and sure it is, in this case it changes a temporary to a global o_O |
| 18:54:55 | <Deewiant> | Vq^: that shouldn't make a difference in terms of memoization, that's just syntax |
| 18:54:55 | <Vq^> | thats somewhat niftier |
| 18:55:02 | <Deewiant> | and that's what I'm confused about |
| 18:55:08 | <Deewiant> | because it is causing memoization |
| 18:55:20 | <bd_> | Deewiant: Consider that you have (!!) (map fib5' [0..]) - a naive implementation would be to put a partial application of (!!) (with the map term bound into a closure) as a global |
| 18:55:20 | <Vq^> | Deewiant: it's like bd_ is saying |
| 18:55:33 | <bd_> | Deewiant: Thus, it's memoized if you don't optimize it much :) |
| 18:55:36 | <Vq^> | Deewiant: the left hand of !! gets stored between the calls |
| 18:55:48 | <Vq^> | Deewiant: because it's not dependent on the argument |
| 18:55:55 | <Deewiant> | bd_: ah, good point, it becomes a closure |
| 18:56:01 | <vixey> | how can you memo typeclasses |
| 18:56:19 | <Deewiant> | I wonder if -O2 slows that down :-D |
| 18:56:37 | <Vq^> | it's a bit tricky to spot which caused my initial confusion |
| 18:56:46 | <Deewiant> | I still wouldn't expect it to happen |
| 18:56:53 | <Deewiant> | now I just understand why it does |
| 18:57:01 | <Vq^> | especially since different implementation handles it differently |
| 18:57:13 | <Deewiant> | but I definitely wouldn't call the "memoized_fib" on that wiki page a memoized version of fib |
| 18:57:25 | <Deewiant> | just one that happens to get memoized depending on how the compiler chooses to generate the code for it |
| 18:57:31 | <Vq^> | Deewiant: not really |
| 18:57:36 | <bd_> | with fib5_, since n is in scope, and since you're light on the optimizations, fib5_' ends up depending on the outer n |
| 18:58:18 | <Vq^> | Deewiant: the function is a value, and all dependencies of that value should really just be computed once |
| 18:58:21 | <Deewiant> | a where- or let- or global binding of fibs = map fib [0..] is what I'd call a memoized one |
| 18:58:45 | <ddarius> | vixey: The intent that is trying to be communicated is the difference between fib n = let memotable = ... in memotable !! n and fib = let memotable = ... in \n -> memotable !! n |
| 18:58:47 | <vixey> | A global definition is equivalent to a let isn't it? |
| 18:58:48 | <Deewiant> | Vq^: should, but nobody's saying you have to |
| 18:59:05 | <Deewiant> | Vq^: there's a bug that GHC doesn't calculate "1 + 2" at compile-time if they're of type Integer |
| 18:59:09 | <bd_> | Deewiant: fib5 is isomorphic to such a binding :) |
| 18:59:18 | <vixey> | ddarius: oh ok |
| 18:59:23 | <vixey> | that makes sense |
| 18:59:39 | <Deewiant> | bd_: sure, but it still depends on the compiler running it through the isomorphism :-P |
| 18:59:54 | <bd_> | Deewiant: not really, the naive implementation of either works similarly :) |
| 19:00:05 | <mauke> | optimisomorphism |
| 19:00:09 | <bd_> | How is 'map fib' any different from '(!!) . map fib' ? |
| 19:00:20 | <Vq^> | Deewiant: you could say that, i would think that it's only a bug if they get recalculated if they isn't part of a function scope |
| 19:00:41 | <Deewiant> | Vq^: it's a global of the form x = 1 + 2 |
| 19:00:51 | <Vq^> | Deewiant: and with optimizations like the one which speeds up fib5_ it should never be recalculated |
| 19:01:36 | <Vq^> | Deewiant: then i would expect it to get recalculated unless the compiler optimizes that by seeing which scopes doesn't depend on the function argument |
| 19:02:41 | <Deewiant> | with ghc -O2 they both appear to run at about the same speed |
| 19:03:20 | <Deewiant> | but I still think it's dependent on a compiler optimization and not memoized in itself |
| 19:03:34 | <Vq^> | only fib5_ |
| 19:03:47 | <Vq^> | fib5 doesn't make that assumption |
| 19:03:48 | <bd_> | Deewiant: check how they're transformed in the core, if you're really curious |
| 19:03:55 | <bd_> | -ddump-stg |
| 19:04:04 | <vixey> | ddarius, how is your linear logic stuff going ? |
| 19:04:10 | <Vq^> | and fib5 is equivalent to memoized_fib in the wiki |
| 19:04:26 | <ddarius> | vixey: I have a parser. I'm not sure what all rules LolliMon uses to loosen up the grammar. |
| 19:04:39 | <vixey> | oh cool |
| 19:05:11 | <vixey> | do you have any repo online ? |
| 19:05:19 | <vixey> | like a darcs thing.. |
| 19:05:51 | <Deewiant> | bd_: I can't read core well enough to see the difference :-) |
| 19:05:55 | <ddarius> | LolliMon accepts a,b -o {c} as being equivalent to a -o b -o {c} which makes sense, but apparently it also accepts a o- sigma U \ f U, top which doesn't make sense syntactically. |
| 19:06:02 | <ddarius> | vixey: No repo, not even locally yet. |
| 19:06:34 | <ddarius> | The next step is either kind/type checking or figuring out how the heck I'm going to evaluate this stuff. |
| 19:06:43 | <vixey> | :D |
| 19:06:54 | <vixey> | I think pfenning has some text on evalution |
| 19:07:22 | <vixey> | some of lolli is described heer http://www.cs.cmu.edu/~fp/courses/linear/handouts.html |
| 19:07:23 | <lambdabot> | Title: 15-816 Linear Logic / Handouts |
| 19:07:36 | <vixey> | iirc... |
| 19:08:55 | <ddarius> | The backward chaining part is easy. The forward chaining probably isn't too hard, but I haven't really thought that hard about it. |
| 19:09:06 | <vixey> | oh I have no idea about forward chaining |
| 19:09:18 | <vixey> | is that how things like: a, b -o c. are evaluated? |
| 19:10:53 | <ddarius> | The monad {_} starts forward chaining. |
| 19:11:11 | <vixey> | oh I see |
| 19:11:25 | <conal> | chessguy: hi |
| 19:11:36 | <chessguy> | howdy |
| 19:11:42 | <sclv_> | I actually don't think that *lisp gave anything especially "nested" at all -- the alpha operator's rules are semantically good to think with though. |
| 19:11:42 | <conal> | chessguy: how's it going? |
| 19:11:47 | <chessguy> | meh, it's going |
| 19:11:57 | <chessguy> | life has been crazy |
| 19:12:47 | <chessguy> | conal: had any chance to look at my code lately? we had talked about trying to figure out why the test harness sucked |
| 19:13:10 | <DRMacIver> | The fact that there are no less than three tools for converting from darcs to git is vaguely unsettling |
| 19:13:29 | <conal> | chessguy: i did look at it some, though i didn't delve deeply enough to find a more elegant angle |
| 19:13:51 | <bd_> | DRMacIver: I tried running one of those on the GHC repo once - darcs proceeded to OOM my machine >_> |
| 19:14:03 | <DRMacIver> | Ha |
| 19:14:09 | <DRMacIver> | I wish I could be surprised by that. :) |
| 19:17:16 | <ddarius> | vixey: If you had a linear context with facts like item(1) and you had the rule item(X), list(XS) -o {list(X:XS)} then if you had the linear fact list([]) then the query {list(XS)} would bind XS to a list of numbers is some non-deterministically chosen order. |
| 19:22:37 | <u_quark> | hello, where can i find some help/documentation on happs ? |
| 19:22:52 | <mauke> | u_quark: the internet |
| 19:23:17 | <chessguy> | conal: the issue seems to be needing a value instead of a type in some places |
| 19:23:39 | <sclv_> | oh hey, it turns out that CM Lisp did provide Nested operations -- it just only parallelized the bottom layer |
| 19:23:39 | <u_quark> | mauke: I need something more specific than that ... |
| 19:24:07 | <mauke> | u_quark: ask a more specific question :-) |
| 19:24:13 | <conal> | chessguy: interesting. do you have an example? |
| 19:24:17 | <mauke> | u_quark: oops, sorry |
| 19:24:31 | <mauke> | u_quark: I actually got confused by a display error in my client. my fault :( |
| 19:24:43 | <u_quark> | lol it's ok |
| 19:26:07 | <chessguy> | conal: ok, so there's this 'perft' function in TestHarness.hs |
| 19:26:32 | <chessguy> | it takes a value of type (Chessboard c) => c, when really all it 'needs' is the type |
| 19:27:28 | <Heffalump> | it doesn't actually have 'c' anywhere else in the type? |
| 19:27:30 | <chessguy> | conal: because any type in Chessboard is going to have a value named 'emptyBoard' |
| 19:28:27 | <conal> | chessguy: i see. sounds like a consequence of having Chessboard be a class rather than a type. |
| 19:28:37 | <chessguy> | conal: indeed |
| 19:29:09 | <chessguy> | because the definition has class Chessboard c where ... emptyBoard :: c |
| 19:29:10 | <Heffalump> | you could wrap it up with an existential |
| 19:29:15 | <Heffalump> | or turn it into a record |
| 19:29:20 | <Heffalump> | (instead of a class) |
| 19:29:51 | <chessguy> | Heffalump: well, the purpose of the class is to define default behavior, but allow it to be overridden |
| 19:30:02 | <Heffalump> | you can do that with a record too |
| 19:30:11 | <hpaste> | koast pasted "(no title)" at http://hpaste.org/8025 |
| 19:30:11 | <Heffalump> | given record update syntax |
| 19:30:45 | <conal> | Heffalump: i wonder if your suggestion would amount to making chessguy's dictionaries explicit. |
| 19:30:52 | <Heffalump> | yes, of course |
| 19:31:00 | <quicksilver> | explicit dictionaries are much better than classes |
| 19:31:05 | <quicksilver> | classes are vastly overused :) |
| 19:31:08 | <Heffalump> | either using existentials or a record type is equivalent to that |
| 19:31:16 | <chessguy> | quicksilver: 'better' in what way? |
| 19:31:26 | <quicksilver> | classes have one specific use case : where you want the type-inference enginge in the compiler to pick the dictionary automatically |
| 19:31:33 | <Heffalump> | indeed, passing an unused value of type 'c' is also equivalent to that, really |
| 19:31:58 | <quicksilver> | chessguy: 'better' in the sense of more general, more flexible, more expressive |
| 19:32:08 | <Heffalump> | quicksilver: agreed, but this might be useful in other cases with this same thing. |
| 19:32:15 | <quicksilver> | of course. |
| 19:32:20 | <quicksilver> | I haven't studied chessguy 's code |
| 19:32:24 | <quicksilver> | just making a general observation |
| 19:32:32 | <Heffalump> | me neither, but it's not stopping me from speculating wildly |
| 19:32:33 | <quicksilver> | classes are overused and dictionaries are more flexible :) |
| 19:33:43 | <chessguy> | yeah, but haskell records suck |
| 19:33:52 | <Heffalump> | not that badly, and not for this purpose |
| 19:33:53 | <quicksilver> | no more than classes |
| 19:33:59 | <lament> | yeah, javascript is much better in that sense ;0 |
| 19:34:02 | <quicksilver> | the syntax is beguilingly similar |
| 19:34:19 | <Heffalump> | also you can't make anonymous type class instances, and you can make anonymous record values |
| 19:34:28 | <quicksilver> | being able to override one member (method) at a time is very handy. |
| 19:34:44 | <quicksilver> | so you can specify behaviour (methods) of one value (object) in terms of another |
| 19:34:52 | <quicksilver> | a bit like what you can do in prototype object systems |
| 19:35:02 | <lament> | yeah, it's very much like javascript |
| 19:48:07 | <wieczyk> | Hi, could someone explain me what is a 'type order' in lambda calculus ? |
| 19:48:52 | <dmwit> | > let fib 0 = 0; fib 1 = 1; fib n | even n = c^2 - a^2 | otherwise = c^2 + b^2 where { n' = div n 2; [a, b, c] = map fib [n'-1..n'+1] } in fib 300 |
| 19:48:54 | <lambdabot> | Exception: stack overflow |
| 19:49:45 | <Philippa_> | wieczyk: doesn't mean anything to me. Is this in the same sense as 'higher-order function'? |
| 19:50:02 | <dmwit> | > let fib 0 = 0; fib 1 = 1; fib 2 = 1; fib n | even n = c^2 - a^2 | otherwise = c^2 + b^2 where { n' = div n 2; [a, b, c] = map fib [n'-1..n'+1] } in fib 300 |
| 19:50:03 | <lambdabot> | 222232244629420445529739893461909967206666939096499764990979600 |
| 19:50:49 | <dmwit> | vixey, Heffalump: Still interested in fib? That one doesn't even use memoization... |
| 19:51:16 | <Heffalump> | interested in what sense? |
| 19:51:26 | <vixey> | that's quite neat :) |
| 19:51:38 | <vixey> | there are lots of ways to do it |
| 19:51:45 | <dmwit> | Dunno, you were talking about it a lot, earlier, but I had to go to lunch with my girlfriend. |
| 19:51:52 | <wieczyk> | Philippa_: well, types with order > 1 are higher-order types. |
| 19:51:56 | <dmwit> | So it took me 'til now to do what I was thinking of. =) |
| 19:52:07 | <Heffalump> | ACTION doesn't even remember that |
| 19:52:09 | <vixey> | well I was just using it to show some details of memoization |
| 19:52:14 | <dmwit> | oh |
| 19:52:17 | <dmwit> | Well, never mind then. |
| 19:52:18 | <wieczyk> | Philippa_: I am studying lambda on my univ now, and i have exercised. But in my point of view i have a mistake in definition of type order |
| 19:52:19 | <dmwit> | =P |
| 19:52:29 | <wieczyk> | Philippa_: but i cannot find any definition on internet. |
| 19:52:46 | <dcoutts> | obk, Heffalump: if you're using the latest Cabal then you can: cabal configure -O0 |
| 19:52:50 | <vixey> | wieczyk: Why would you want a definition of this word? Where does it come from? |
| 19:53:06 | <wieczyk> | Philippa_: I have defintion order(t0 -> t1 -> ... -> tn -> a) = 1 + max(1, t0, ..., tn) |
| 19:53:06 | <vixey> | s/word/phrase/ |
| 19:53:11 | <obk> | dcoutts: Sure, but anyone downloading the package wouldn't know to do so |
| 19:53:20 | <wieczyk> | vixey: on my home-work list :) |
| 19:53:32 | <vixey> | what exactly is on your list? |
| 19:53:38 | <wieczyk> | and in my opinion it should be 1 + max (_0_,...) |
| 19:53:46 | <wieczyk> | not 1 + max (1,...) |
| 19:54:00 | <Socrates`> | Is it possible to do type class constraints in a data definition? |
| 19:54:05 | <dcoutts> | obk: oh you mean it fails with -O1 ? yeah, that'd be bad :-) |
| 19:54:23 | <ddarius> | Well max(0, ...) is the same as max(...) in this case. |
| 19:54:27 | <obk> | dcoutts: Just '-O' which AFAIR is the same as '-O1' |
| 19:54:35 | <obk> | yes, it is bad :-) |
| 19:54:40 | <wieczyk> | vixey: hm |
| 19:54:42 | <vixey> | shouldn't it be |
| 19:54:44 | <dcoutts> | obk: yes, I was just making it explicit |
| 19:54:54 | <dcoutts> | obk: btw, we are going to use something like make, there's a GSoC project to do a implementation of a make-style framework in Haskell |
| 19:54:55 | <Socrates`> | So, say rather than Maybe a, you could constrain a to say (Monad m) => m a? |
| 19:54:56 | <vixey> | 1 + max(1, order(t0), ..., order(tn)) |
| 19:55:10 | <ddarius> | Also, presumably that should be max(order(t0), order(t1), ... ) |
| 19:55:16 | <obk> | dcoutts: Nice! Do you have a URL for it? |
| 19:55:25 | <wieczyk> | dcoutts: i need to proof some easy think at start, that order(t) = 1 => t = a |
| 19:55:27 | <vixey> | it's probably not worth defining this yourself |
| 19:55:40 | <vixey> | if it's used in any proofs you can just figure out what the definition should be |
| 19:55:47 | <wieczyk> | and type syntax, t = a | t -> t |
| 19:56:17 | <wieczyk> | it means that a is a type variable, and also some function type is a type. |
| 19:56:18 | <wieczyk> | and |
| 19:56:19 | <dcoutts> | obk: http://code.google.com/soc/2008/haskell/appinfo.html?csaid=56D60241D77CA94C |
| 19:56:20 | <lambdabot> | Title: Google Code - Summer of Code - Application Information, http://tinyurl.com/62c6aw |
| 19:56:21 | <vixey> | wieczyk: Do you have some test cases? |
| 19:56:37 | <vixey> | wieczyk: like order(x) = 1, order((a -> b) -> a -> b) = 2 ? |
| 19:56:40 | <obk> | dcoutts: Thanks! I'll give it a look |
| 19:57:00 | <wieczyk> | and, if i need to proof order(t) = 1 => t = a, it means that first-order are type-variables, not type of functions. But, |
| 19:57:09 | <wieczyk> | order(a) = 1 + max(1) = 1 + 1 = 2 |
| 19:57:23 | <wieczyk> | that i have mistake in defintion of order(t) ? |
| 19:57:59 | <wieczyk> | becuase, if order(a) = 2 by using this defintion, that i cannot proof "order(t) = 1 => t = a" |
| 19:59:16 | <wieczyk> | Ah. |
| 19:59:27 | <wieczyk> | a lecturer send a info that it should be 0 in max() |
| 19:59:29 | <wieczyk> | sorry for problem. |
| 19:59:40 | <wieczyk> | btw: do yo know some good papers for lambda ? |
| 19:59:47 | <nottha_k> | what does it mean when a package is hidden? http://hpaste.org/8026 |
| 20:00:11 | <ddarius> | wieczyk: There is tons of good information on the lambda calculus. Just put it into google or google scholar. |
| 20:00:39 | <dmwit> | nottha_k: It means you need more packages in the build-depends: line in the .cabal file. |
| 20:01:09 | <dmwit> | (...I think.) |
| 20:02:13 | <nottha_k> | dmwit: sounds right. I added "time" to the list of dependencies and got a little farther |
| 20:02:16 | <nottha_k> | thanks |
| 20:03:08 | <oldsalt> | @seen shag |
| 20:03:08 | <lambdabot> | Plugin `seen' failed with: too few bytes. Failed reading at byte position 8 |
| 20:03:31 | <mauke> | preflex: seen shag |
| 20:03:31 | <preflex> | Sorry, I haven't seen shag |
| 20:04:21 | <oldsalt> | mauke: thx ;) |
| 20:05:15 | <dmwit> | So, \bot mostly replies to commands that start with ? or @. |
| 20:05:32 | <dmwit> | But she also has a tinyURL plugin and a title-grabbing plugin. |
| 20:05:35 | <dmwit> | Are there any others? |
| 20:05:45 | <dmwit> | (:t, :k, > don't count.) |
| 20:05:47 | <mauke> | karma, presumably |
| 20:05:52 | <dmwit> | Ah, karma. |
| 20:07:09 | <dons> | Igloo: the "GHC 6.8.2 and large source files" mail looks like a good test case generator |
| 20:07:16 | <Corun> | Ok, ok, it's not haskell.. But isn't this seriously awesome: http://www.youtube.com/watch?v=NHC_Qyov2Xc |
| 20:07:16 | <lambdabot> | Corun: You have 1 new message. '/msg lambdabot @messages' to read it. |
| 20:08:01 | <Frederick> | folks does soneone here had a good course in semantics on the university and can point me out the website for it so I can get exercises and solutions? |
| 20:09:03 | <Baughn> | Frederick: Semantics of what? |
| 20:10:44 | <Igloo> | dons: *nod*, and we have some other test cases to look at along similar lines, too |
| 20:13:08 | <Frederick> | Baughn: imperative languages |
| 20:13:17 | <Frederick> | Denotational Semantics |
| 20:15:38 | <int-e> | dcoutts: you have a typo in the gtk2hs motd - it's haskell.org, not hsakell.org |
| 20:15:49 | <dcoutts> | doh |
| 20:16:07 | <dcoutts> | int-e: fixed thanks |
| 20:17:30 | <dmwit> | Good thing we have wetware spelling correctors. |
| 20:21:01 | <Frederick> | Baughn: suggestions? |
| 20:21:18 | <Baughn> | Frederick: Apparently not. I haven't seen it, and google is helpless. |
| 20:21:43 | <hpaste> | (anonymous) pasted "(no title)" at http://hpaste.org/8027 |
| 20:22:03 | <Frederick> | Baughn: not sure if google is helpless but I could not find the right terms |
| 20:22:06 | <int-e> | dmwit: actually I pasted the command (it's a darcs pull <url>) and only spotted the mistake after that failed. so it was computer aided spell checking. |
| 20:23:09 | <dmwit> | oh, heh |
| 20:24:25 | <dons> | int-e: good work on the git/darcs tool |
| 20:24:35 | <dons> | you should probably cc. the darcs list too |
| 20:25:08 | <dons> | Igloo++ Serge sez: "But I think that you have found a bug in the DoCon test program. |
| 20:25:12 | <dons> | Thank you" |
| 20:25:28 | <dons> | i wonder when we'll see docon on hackage. |
| 20:27:00 | <dons> | ah, it is even cabalised. |
| 20:27:25 | <int-e> | dons: maybe I'll do that for 0.2. right now it's a bit painful to build - it's really of little interest to people who don't know haskell. |
| 20:28:19 | <dons> | ACTION tries: cabal install docon |
| 20:28:37 | <dcoutts> | ACTION crosses his fingers on dons behalf |
| 20:28:42 | <dons> | 20k lines of code. |
| 20:29:13 | <dons> | dcoutts: its all nicely cabalised, http://haskell.org/docon/distrib/2.11/ |
| 20:29:22 | <dons> | we just need to convince serge to upload the source/ bundle |
| 20:29:49 | <dcoutts> | oh right |
| 20:30:17 | <int-e> | Oh and I've learned that the darcs repository at darcs.net is slightly inconsistent - at one point there's a patch that renames a Autoconf.lhs file that was never created. |
| 20:31:18 | <dons> | wow, this really does take a while to compile |
| 20:31:25 | <dons> | [22 of 83] Compiling VecMatr |
| 20:31:30 | <dons> | 3 minutes in. |
| 20:31:50 | <dons> | ghc's doing ok though. 133M heap |
| 20:33:09 | <dons> | docon needs a better website, and haddocks |
| 20:38:39 | <dons> | half way.. |
| 20:38:55 | <ddarius> | Conal Elliott and Frank Pfenning. A family of program derivations for higher order unification. |
| 20:39:49 | <dons> | that must have been a while ago, ddarius |
| 20:39:53 | <Peaker> | I converted my ray tracer from using a 2d Array of (Word8, Word8, Word8) to represent the pixels, to a 2d Array of Vector (where: data Vector = Vector (Double, Double, Double)) - this made it a _lot_ slower. Also, just converting from that format back to the array of (Word8,Word8,Word8) takes a looong time. Why is that? |
| 20:40:02 | <dcoutts> | ACTION piles in on the QC library testing debate |
| 20:40:07 | <ddarius> | dons: 1987 |
| 20:40:07 | <dons> | oh horrible, you use triples, Peaker? |
| 20:40:25 | <Peaker> | dons, yeah, a Vector is a triplet/tuple yeah |
| 20:40:35 | <ddarius> | Vector3 !Double !Double !Double |
| 20:40:36 | <Peaker> | dons, mainly for 3d coordinates but now I am using it for r,g,b colorspace, heh |
| 20:40:41 | <dcoutts> | Peaker: if you're worrying about performance there are much better representations |
| 20:40:51 | <Peaker> | dcoutts, I'm pretty new at this :) |
| 20:40:57 | <Peaker> | ddarius, thanks I'll try that |
| 20:41:04 | <dcoutts> | you can do better still |
| 20:41:14 | <hpaste> | dons pasted "standard vector type for Double" at http://hpaste.org/8029 |
| 20:41:16 | <dcoutts> | eg use a UArray Int Word32 |
| 20:41:28 | <ndm> | dons, dcoutts: not tempted to start using Lazy SmallCheck rather than QuickCheck |
| 20:41:41 | <dcoutts> | ndm: what makes it Lazy? |
| 20:41:46 | <ndm> | its become to tool of choice for testing - the tests mean something, you can keep them going to get more results etc. |
| 20:41:52 | <dons> | ndm, we already use smallcheck + quickcheck + chasing bottoms |
| 20:41:55 | <dcoutts> | ndm: I have indeed used SmallCheck and it's great for some situations |
| 20:42:06 | <ndm> | dcoutts, think of it as smallcheck but more efficient - lazy is just an implementation detail |
| 20:42:15 | <dons> | do smallcheck for the 'inductive' cases, quickcheck for random extra wandering, and bottom testing for other things. |
| 20:42:24 | <Peaker> | dcoutts, I want a 2d array (UArray (Int,Int) ..)? |
| 20:42:27 | <ndm> | lazysmallcheck is loads faster, especially if you do validitycondition => test |
| 20:42:28 | <conal> | i'd like some help with ghc inlining & rules. i have a rule that would fire if 'id' is inlined and simplified. it won't fire unless i add a simplification rule saying "id = \ x -> x". |
| 20:42:29 | <Peaker> | dcoutts, why Word32 and not Vector? |
| 20:42:32 | <dcoutts> | dons, ndm: I should tidy up my SmallCheck strictness checking variation and release it as StrictCheck |
| 20:42:50 | <dcoutts> | ndm: ah I see |
| 20:42:59 | <Peaker> | dons, why the pragma there? |
| 20:43:09 | <dons> | Peaker: so it doesn't use slow Double math ops |
| 20:43:15 | <dons> | Peaker: also -fvia-C -optc-O2 |
| 20:43:22 | <Peaker> | dons, will -O3 do? |
| 20:43:26 | <dons> | nothing |
| 20:43:30 | <dcoutts> | Peaker: an Array of a structure type has to use pointer indirections to other heap allocated objects |
| 20:43:45 | <Peaker> | dons, what does the unpack do to avoid double math ops? |
| 20:43:53 | <dons> | conal: have you checked out the rewrite rules wiki page? |
| 20:43:55 | <dcoutts> | Peaker: so for maximum performance we do not want to do that, we want to store the colour components directly in the array |
| 20:44:07 | <conal> | dons: no, i haven't. looking ... |
| 20:44:07 | <Peaker> | dcoutts, but I want a 2d array of vectors, how do I store a vector in a Word32? |
| 20:44:16 | <dcoutts> | Peaker: and 3 Word8's fit comfortably into a Word32 |
| 20:44:33 | <ndm> | ACTION has just finished 0.5 billion lazy small check tests |
| 20:44:33 | <Peaker> | dcoutts, ah, but I want to be able to do interesting things to colors.. like averaging them - which is difficult when they wraparound as you add them |
| 20:44:34 | <dons> | conal: http://haskell.org/haskellwiki/GHC/Using_rules |
| 20:44:42 | <dons> | ndm, don't tell ian. |
| 20:44:52 | <dcoutts> | Peaker: it'd require store/fetch functions that pack/unpack |
| 20:44:55 | <ndm> | dons: only took 2 days :) |
| 20:45:07 | <ndm> | would hardly make a dent on the buildbots... |
| 20:45:12 | <dons> | docon now up to 50/80 modules |
| 20:45:19 | <conal> | dons: thanks much! |
| 20:45:28 | <dcoutts> | ndm: actually they're pretty sensitive to build times for validation |
| 20:45:40 | <dcoutts> | ndm: since that's part of their development cycle |
| 20:45:44 | <ndm> | dcoutts, i know - was joking :) |
| 20:45:54 | <Peaker> | dons, thanks for the tips |
| 20:46:29 | <ndm> | dcoutts, for filepath i use the policy of having quickcheck tests and unit tests, and if a quickcheck one ever fails i make that particular case (or a minimal variant) a unit test |
| 20:46:41 | <dcoutts> | ndm: pretty sensible |
| 20:46:48 | <DRMacIver> | Idle thought based on current libraries mailing list discussion. How hard would it be to create a setup where a set of quickcheck tests generated a file which creates test cases for the failures |
| 20:47:14 | <sclv_> | ndm: not to bug you, but did you get my lamdbabot msg? |
| 20:47:24 | <DRMacIver> | so you had developers running fullblown QC tests and the failures generated tests that could be added to the nightlies |
| 20:47:24 | <ndm> | DRMacIver: ever tried to do a test setup using cabal? now that's painful! - we need that infrastructure to work basicially before you do anything more |
| 20:47:37 | <DRMacIver> | Heh. No, I admit I haven't. |
| 20:47:41 | <ndm> | sclv_: nope, lambdabot often looses messages, or repeats them |
| 20:48:00 | <dcoutts> | ndm: I consider it non-existent :-) |
| 20:48:02 | <DRMacIver> | The number of serious Haskell projects I've written is sadly rather minimal |
| 20:48:19 | <dcoutts> | ndm: the support for tests/testing in Cabal |
| 20:48:42 | <ndm> | dcoutts, there is a badly designed hook with a constantly changing interface - what more would i want ;) |
| 20:48:47 | <sclv_> | ndm: if you're not already all set with a testing harness for hoogle4, I have my quickcheck based cgiCheck in a repo now. |
| 20:48:56 | <sclv_> | http://code.haskell.org/~sclv/cgicheck/ |
| 20:49:09 | <dcoutts> | ndm: oh it's only badly designed, it's not constantly changing |
| 20:49:37 | <ndm> | dcoutts, it changed at least once, going from returning an ExitCode to () - or vice versa |
| 20:49:37 | <sclv_> | its usable, but not fully tested and sorta rough in terms of some api refinements -- I want to be able to insert random delays, for example, to force more concurrency issues. |
| 20:49:51 | <dcoutts> | ndm: oh, right, yeah ok :-) |
| 20:50:25 | <dcoutts> | ndm: I was going to say we've gone so far to maintain stability that we have an extra parmater to test that does nothing and we can't even figure out what it was ever for :-) |
| 20:50:33 | <ndm> | sclv_: Hoogle is entirely stateless, and i've been working on the pure test framework, using the console version - but i'll put this in the pile to check out when the CGI is ready for testing |
| 20:51:07 | <dons> | i'd be interested in seeing short runs each night, but seeded with new seeds |
| 20:51:22 | <ndm> | dcoutts, cabal-install makes me sufficiently happy that, provided it is bundled with the next full GHC release, i can forgive cabal a lot for the meantime |
| 20:51:26 | <dons> | over time you'd get rather good exploration of the value space. this is what john hughes set up for the ericcson guys |
| 20:51:53 | <dcoutts> | dons: right |
| 20:52:10 | <dcoutts> | dons: with a high 'size' on the Arbitrary instance |
| 20:52:41 | <ndm> | what you really want is one property language and instance declration structure that can do smallcheck, lazysmallcheck and quickcheck with a simple change of driver call |
| 20:53:01 | <ndm> | i bring this up with colin once a month, just to keep the idea floating around |
| 20:53:02 | <dcoutts> | ndm: but you'd write your properties differently I think |
| 20:53:10 | <sclv_> | ndm: it works pretty well for stateless stuff already actually -- just an easy way to generate and run requests with conditions on the responses. I might have just reinvented a subset of quickCheckM, I guess, but it seems pleasant enough to use for me. |
| 20:53:11 | <ndm> | dcoutts: how? |
| 20:53:15 | <monochrom> | ACTION has successfully built the ghc 6.8.3 release candidate (6.8.2. may 31) |
| 20:53:24 | <dcoutts> | ndm: especially between sc and qc |
| 20:53:31 | <ndm> | sclv_: i will check it out once i get there |
| 20:53:44 | <dcoutts> | ndm: because you have to worry about the size of the state space with SC |
| 20:53:47 | <ndm> | dcoutts, sc has existentials and uniques - but is a superset of qc |
| 20:54:04 | <ndm> | i've never had to worry with sc |
| 20:54:15 | <ndm> | but lazy small check is a lot better for that, which is what i always jump for |
| 20:54:35 | <dcoutts> | ndm: if your branching factor is too high then you cannot test to depth N where N = ?? |
| 20:55:28 | <ndm> | dcoutts, lazy small check :) - it matters less about the branching factor of the data type, and more about the branching factor of your test |
| 20:55:29 | <dcoutts> | ndm: if there is a way to limit the total number of tests with SC then that point is moot |
| 20:55:42 | <sclv_> | yeah, don't mean to be pushy, just looking for use-cases/feedback. |
| 20:55:46 | <ndm> | and if your test has a high branching factor, more tests is probably a good idea |
| 20:56:00 | <dcoutts> | ndm: sure but time is a limitation |
| 20:56:04 | <ndm> | sclv, no worries - will probably be a few weeks but do want to give it a whirl |
| 20:56:33 | <ndm> | dcoutts, i've been using it to "prove" parts of my phd - small phd (relatively), and large computers for a weekend :) |
| 20:56:51 | <dcoutts> | ndm: one thing I worry about for SC/QC is that different tests actually need different test generators for the same types in different tests |
| 20:57:01 | <monochrom> | wow, ghc src + extralib build tree (source + binary) is approaching 1GB. :) |
| 20:57:57 | <dcoutts> | ndm: especially in SC actually, eg Char, in testing bytestring. What chars values do you allow? |
| 20:58:05 | <ndm> | dcoutts, you are like a sales pitch for lazy small check - you just generate everything |
| 20:58:09 | <dcoutts> | ndm: not too many or the branching factor is insane |
| 20:58:30 | <ndm> | dcoutts, lazysmallcheck reigns in the branching with some very clever tricks :) |
| 20:58:41 | <dcoutts> | ndm: it's not about the number that get eliminated, it's the number you actually test with |
| 20:58:52 | <ndm> | dcoutts, it eliminates them before generating them |
| 20:59:07 | <ndm> | i.e. if you test all (== 'a') xs |
| 20:59:09 | <dcoutts> | ndm: so you just add lots of ==> filters and it's all ok |
| 20:59:21 | <ndm> | it will generate x:xs, for all x in Char |
| 20:59:34 | <ndm> | but will only generate 'a':x:xs |
| 20:59:54 | <ndm> | dcoutts, you do nothing, it understands your code, and doesn't even generate "dull" cases |
| 21:00:16 | <ndm> | ==> filters do the trick, but so does anything, the property itself, whatever |
| 21:00:29 | <dcoutts> | ndm: how does it know from looking at all (== 'a') xs that we only want 'a' values in some cases? |
| 21:00:54 | <dcoutts> | isn't the (a -> Bool) part of the property a black box? |
| 21:01:01 | <ndm> | dcoutts, laziness - it tries with 'b':_|_, sees you never evaluated _|_, and figures that all other tests are irrelevant |
| 21:01:11 | <dcoutts> | ohhh, sneaky |
| 21:01:17 | <dcoutts> | using _|_'s |
| 21:01:17 | <ndm> | its a black box unless you have impure exceptions, or IORefs |
| 21:01:23 | <ndm> | yeah, its very neat |
| 21:01:44 | <ndm> | means you don't need to trick out your generators, and it exploits laziness in properties automatically |
| 21:02:01 | <dcoutts> | ndm: sounds very much like the strictness adaptations I made to SC but with a different purpose |
| 21:02:29 | <dcoutts> | ndm: LSC uses it to see what was evaluated and guide further tests, I was using it to actually test properties at all partial values |
| 21:02:57 | <ndm> | yes, does sound similar |
| 21:03:05 | <dcoutts> | ndm: and there's an example where you do need different properties again, eg with partial values you don't need any pre-conditions :-) |
| 21:03:50 | <dcoutts> | mind you strictness properties are always going to be different |
| 21:04:15 | <ndm> | yeah |
| 21:04:22 | <dcoutts> | it might be useful to test ordinary properties with partial values too though |
| 21:04:25 | <ndm> | although a sufficiently generic generator could get them all |
| 21:04:39 | <ndm> | hmm, not sure - you are likely to get partial values back |
| 21:04:41 | <dcoutts> | eg to distinguish reverse . reverse /= foldr (:) [] |
| 21:05:01 | <ndm> | ok, partial as in infinite, rather than _|_ |
| 21:05:05 | <dcoutts> | both |
| 21:05:08 | <dcoutts> | all partial values |
| 21:05:25 | <dcoutts> | eg _|_, _|_ : _|_, 0 : _|_, etc etc |
| 21:05:54 | <dcoutts> | the ordinary SC generators but extended to generate _|_ as the initial value for every type |
| 21:06:10 | <dcoutts> | so you generate all partial and total values in domain order |
| 21:06:11 | <ndm> | yeah |
| 21:06:46 | <dcoutts> | and you can borrow the === and <== domain equality and refinement operators from the ChasingBottoms lib |
| 21:06:57 | <dcoutts> | that's basically what I did |
| 21:07:35 | <dcoutts> | perhaps I should talk to Colin about doing and releasing a variation like that |
| 21:08:34 | <ndm> | yep, you should! |
| 21:09:21 | <monochrom> | chasing bottoms sounds fun |
| 21:09:52 | <dcoutts> | @slap monochrom |
| 21:10:08 | <dcoutts> | @botsnack? |
| 21:10:38 | <dcoutts> | monochrom: ah well, no wet fish for you |
| 21:10:44 | <monochrom> | haha |
| 21:11:41 | <jaj> | @b52s |
| 21:12:03 | <jaj> | lazy evaluation... |
| 21:14:58 | <dcoutts> | @seen dbueno |
| 21:15:33 | <dcoutts> | doh! lambdabot must be asleep |
| 21:15:47 | <EvilTerran> | doh |
| 21:16:12 | <jaj> | @slap lambdabot |
| 21:17:55 | <hpaste> | petekaz pasted "Strictness question" at http://hpaste.org/8032 |
| 21:18:11 | <hpaste> | conal pasted "rewrite example -- why doesn't id inline?" at http://hpaste.org/8033 |
| 21:19:22 | <conal> | i'd appreciate tips on my paste. i'm trying to figure out when i can count on inlining to help with rule applicability. |
| 21:19:52 | <dons> | conal: ah, maybe both id and reverse inline at the same time |
| 21:20:03 | <dons> | you'd have to delay inlining on 'reverse' I think |
| 21:20:05 | <petekaz> | I'm reading dons on exploiting strictness, laziness, and recursion. In his definition of length', I asked at one point why 'go' doesn't accumalate thunks due to the (n+1). Someone told me ghc figures it out all by itself. So why then do I need to be explicit in my definition of 'mean'? |
| 21:20:06 | <SamB> | hmm. |
| 21:20:17 | <conal> | dons: oh |
| 21:20:25 | <conal> | dons: oh! that makes sense. |
| 21:20:39 | <conal> | dons: and my rule pseudo-inlined id early |
| 21:20:43 | <SamB> | dons: did you know that unstream doesn't seem to have any progress guarentees? |
| 21:20:50 | <dons> | conal, yeah, that's it. |
| 21:20:54 | <dons> | i just got it to work. |
| 21:21:10 | <conal> | dons: thanks. okay, now i'll see what i can make of my *real* example. |
| 21:21:16 | <dons> | SamB: sure. you can Skip forever. its not "progress" though, talk to dcoutts. |
| 21:21:22 | <monochrom> | Perhaps using a tuple blinds the strictness analyzer. |
| 21:21:35 | <SamB> | dons: why do you say it's not progress? |
| 21:21:43 | <hpaste> | dons pasted "control inlining of what you wish to match" at http://hpaste.org/8034 |
| 21:21:47 | <SamB> | coq won't let me write it, that's all I'm sayin' ;-) |
| 21:21:49 | <dons> | conal: ^ |
| 21:22:30 | <ddarius> | petekaz: go is strict in n, that foldl' is not strict in the components of the tuple (without the !s) although the overall function is strict. |
| 21:22:45 | <ddarius> | petekaz: Personally, I dislike relying on anything but very basic strictness analysis. |
| 21:24:13 | <conal> | dons: :). simple enough. does all inlining happen after all rewriting? |
| 21:25:11 | <petekaz> | ddarius: ok, thanks. |
| 21:25:51 | <petekaz> | ddarius: I guess when I read his post, I would have preferred to see 'go' written wia bang pattern just to be explicit. |
| 21:26:08 | <petekaz> | I'm a newbie so what do I know anyways. |
| 21:26:10 | <dons> | conal: its interleaved. see -ddump-simpl-iterations |
| 21:26:22 | <dons> | you get a phase of different inlinings, then rules, then repeat 3 or 4 times |
| 21:26:24 | <dons> | or more.. |
| 21:26:30 | <ddarius> | petekaz: Extraneous strictness annotations can decrease performance and that go in length is strict. |
| 21:26:49 | <ddarius> | (in this case, I doubt it would hurt) |
| 21:26:53 | <dons> | i think if you've determined the precise strictness you want, making it explicit is a good idea though |
| 21:27:03 | <dons> | as for type annotations |
| 21:28:49 | <petekaz> | ddarius: why is the go in length strict? is it only because of the strictness analysis? or are you saying it is strict regardless? |
| 21:29:20 | <petekaz> | wouldn't the (n+1) just start accumulating thunks? |
| 21:29:37 | <dons> | since it is an Int, ghc can see through to the strictness of +# |
| 21:29:48 | <monochrom> | ghc -O0 will thunk it. |
| 21:29:52 | <dons> | which works for nice atomic types like Word, Int, etc. |
| 21:29:58 | <dons> | but relies on -fstrictness |
| 21:29:58 | <monochrom> | @quote thunk |
| 21:30:00 | <ddarius> | I'm saying semantically go is strict whereas that foldl' is not strict in the components of the pair without those bangs. |
| 21:30:28 | <dons> | right. foldl' is kinda broken :) |
| 21:30:37 | <ddarius> | dons: How so? |
| 21:30:37 | <dons> | we need foldl_rnf |
| 21:30:56 | <dons> | its only whnf strict in the accumulator, partially, which confuses people |
| 21:31:00 | <ddarius> | Blech, we need a library of strict types (which we have now, no?) |
| 21:31:04 | <dons> | right. |
| 21:31:11 | <dons> | cabal install strict , peoples! |
| 21:31:20 | <dons> | probably should be in base though, with more access to the NF class |
| 21:31:34 | <ddarius> | It should only reduce to whnf. rnf is almost certainly way too much. |
| 21:31:58 | <dons> | yeah, it'd be interesting to think about what it would take to get (Int,Int) into (# Int#, Int# ) in an accumulator |
| 21:32:14 | <monochrom> | superfoldl' :: NFData b => (b -> a -> b) -> b -> [a] -> b :) |
| 21:32:15 | <dons> | rnf would work, but could whnf + a bit of the nested CPR analysis (or something like it) |
| 21:32:35 | <dons> | really, folds are great if you can use tuples to describe register variable layout |
| 21:33:01 | <dons> | ACTION thinks we understand what ghc does a lot more than 5 years ago |
| 21:33:14 | <ddarius> | rnf would turn foldl' (flip (:)) [] from O(n) into O(n^2) |
| 21:33:33 | <SamB> | ACTION defines instead a function streamSteps which returns the coq equivalent of [Maybe a] (with a co-inductive list type) |
| 21:33:55 | <dons> | SamB: oh, you should check Jeremy gibbons paper with the correctness proof for streams |
| 21:34:00 | <dons> | formalising that would be an awesome HW paper... |
| 21:34:08 | <dons> | or mechanising metatheorey |
| 21:34:26 | <dons> | you could write it with swiert |
| 21:34:32 | <dons> | he's done a few coq papers, iirc |
| 21:35:35 | <dons> | SamB: http://www.comlab.ox.ac.uk/jeremy.gibbons/publications/adt.pdf |
| 21:35:35 | <SamB> | heh |
| 21:36:02 | <dons> | seriously, proving some nice thinks about the stream-fusion combinators would be an ICFP worthy paper |
| 21:36:44 | <SamB> | I mean ... like I have time to actually write a paper! |
| 21:36:47 | <SamB> | I've got classes |
| 21:37:03 | <dons> | well, do the proofs, i'll help you write the paper :) |
| 21:37:13 | <dons> | ACTION loves how academia works |
| 21:38:04 | <SamB> | hmm, nice hint here... |
| 21:38:22 | <SamB> | two types are different if there is an experiment that shows this, and not different otherwise |
| 21:38:25 | <SamB> | er. |
| 21:38:27 | <SamB> | values. |
| 21:39:19 | <dcoutts> | observational equality |
| 21:39:53 | <SamB> | yes, but the key there is that I should define inequality inductively, and simply define equality as the negation |
| 21:40:25 | <dons> | jeremy's paper is quite nice. i should reread it every 6 months till i remember the approach |
| 21:41:15 | <dons> | dcoutts: was jeremy's paper published in the end? |
| 21:41:33 | <dcoutts> | dons: not at ICFP last summer, perhaps elsewhere |
| 21:41:46 | <dons> | its the kind of thing we want to integrate into the jfp stuff |
| 21:41:52 | <monochrom> | Nice, it begins with "Dijkstra". :) |
| 21:42:01 | <dons> | that, and janis' two papers that cover streams |
| 21:42:39 | <dons> | and the constructor specialisation paper. and now also the story for SAT in ghc, and nested CPR |
| 21:42:47 | <dons> | fills out the performance story, and the correctness story |
| 21:43:10 | <dons> | we can end the paper with one of those little QED boxes. [] |
| 21:43:14 | <dcoutts> | dons: yes I need to re-read it for one of my thesis chapters |
| 21:43:57 | <dons> | dcoutts: http://scholar.google.com/scholar?hl=en&lr=&safe=off&cites=8061486271207904370 |
| 21:44:22 | <dons> | crikey, we got cited in a javascript paper.. |
| 21:44:45 | <dcoutts> | heh heh |
| 21:44:51 | <SamB> | isn't that good? |
| 21:44:53 | <dons> | dcoutts, "Putting declarative programming into the web: translating curry to javascript" |
| 21:44:58 | <dons> | well, so it is a haskell guy. |
| 21:45:30 | <monochrom> | http://www.comlab.ox.ac.uk/jeremy.gibbons/publications/#adt says "submitted for publication, January 2008" but it doesn't say where and what is happening. |
| 21:46:06 | <monochrom> | ACTION personally prefers links like that to going straight to the pdf. |
| 21:46:20 | <dons> | jan 08, ok. so that's something new. |
| 21:46:29 | <SamB> | monochrom: me too |
| 21:47:14 | <dcoutts> | dons: I'll have to find out since I'll be citing it |
| 21:47:18 | <monochrom> | My heuristic guesses that it is submitted to something like Formal Aspects of Computing due to the long time between submission and hearing back. :) |
| 21:47:39 | <BONUS> | ugh i still can't decide whether to buy Programming in Haskell or not :[ |
| 21:48:30 | <dcoutts> | BONUS: let me help you: yes. :-) |
| 21:48:45 | <dcoutts> | BONUS: did you read my review? |
| 21:50:04 | <ddarius> | ACTION has inadvertently stumbled over an answer to his lollimon syntax question. |
| 21:50:07 | <BONUS> | no i didnt |
| 21:50:32 | <BONUS> | i kind of heard that it's good but very, er, beginner-ish |
| 21:50:48 | <BONUS> | and i already know all the beginner stuff and some intermediate stuff |
| 21:51:20 | <ddarius> | Get Algebra of Programming |
| 21:51:24 | <dcoutts> | BONUS: http://www.cs.nott.ac.uk/~gmh/coutts.pdf |
| 21:51:26 | <monochrom> | Haha |
| 21:51:47 | <BONUS> | thanks i'll read that |
| 21:51:48 | <BONUS> | hmm |
| 21:52:20 | <BONUS> | dcoutts what did you use to typeset this? |
| 21:52:45 | <dcoutts> | BONUS: latex with The Monad.Reader style sheet |
| 21:53:14 | <BONUS> | yeah i thought it was latex but it looks more awesome hehe |
| 21:53:17 | <dons> | docon is still compiling.. |
| 21:53:24 | <BONUS> | what's the documentclass used |
| 21:53:47 | <dcoutts> | BONUS: yeah it's nice, check The Monad.Reader advise for authors, it's got all the stuff |
| 21:53:53 | <dons> | this thing is amazing, Igloo , [67 of 83] after an hour. |
| 21:53:53 | <dcoutts> | advise/advice |
| 21:54:13 | <BONUS> | kewl |
| 21:54:13 | <dcoutts> | dons: heh heh |
| 21:54:21 | <dcoutts> | dons: at -O2 right? |
| 21:54:41 | <dcoutts> | dons: clearly we need parallel build in Cabal |
| 21:54:47 | <dons> | dcoutts: yeah. -O2 |
| 21:55:10 | <dons> | serge's done an awful lot of work here. docon is one of the most underappreciated large haskell systems |
| 21:55:22 | <dcoutts> | ACTION wastes 3/4 cores, 3/4 of the time |
| 21:55:30 | <dcoutts> | dons: yes, he's terrible at publicity :-) |
| 21:55:34 | <Lycurgus> | on what kind of CPU? |
| 21:55:35 | <dons> | hey, reminds me, i wonder if my fibonacci primes is still running |
| 21:56:02 | <dons> | aweseoe, 275432.58835s 34 prime=104911 |
| 21:56:17 | <Lycurgus> | (i.e the docon compile) |
| 21:56:29 | <dons> | i've been borrowing 3 cores on a server for a week now. |
| 21:56:42 | <dcoutts> | I bet it's warm |
| 21:57:03 | <dons> | well, we just have to get to prime 40 for new results. |
| 21:58:16 | <dcoutts> | dons: is that CPU seconds or real seconds? |
| 21:58:24 | <dcoutts> | dons: ie 3 CPU days or 1 real day? |
| 21:59:03 | <dcoutts> | dons: and the time doubles for each one right? |
| 21:59:09 | <dons> | roughly doubles, yep. |
| 21:59:39 | <dons> | its this program , with a few custom dons(TM) tweaks, |
| 21:59:40 | <dons> | http://haskell.org/haskellwiki/Fibonacci_primes_in_parallel |
| 21:59:44 | <dcoutts> | dons: so you're looking at ~64 days for 40 |
| 21:59:48 | <dons> | the most useful program with `par` in it i've seen so far. |
| 22:00:03 | <dons> | hey, that's not too bad. the guy i'm competing against had 3.5 years to get to 37 |
| 22:00:11 | <dcoutts> | ooh |
| 22:01:15 | <dons> | http://www.gristle.to/markup/primes/ppfibs.html |
| 22:01:33 | <dons> | actually, he says, "34. fibonacci (104911) is probably prime " |
| 22:01:44 | <dons> | so i think that means he found a bug in his program, and had to start over. |
| 22:02:26 | <shepheb> | if I want to fiddle with 6.9 on x86 Linux 32bit, should I grab the HEAD? Is there a way to check if there are any recent nightly builds that worked on my platform? |
| 22:03:25 | <hpaste> | Twinside pasted "(no title)" at http://hpaste.org/8036 |
| 22:03:38 | <Twinside> | why ghc give me an error when i put a type signature which is the same that the inferred one? |
| 22:08:15 | <MyCatVerbs> | Twinside: that sounds strange. hpaste the code and the error, please? |
| 22:08:38 | <Twinside> | http://hpaste.org/8036 :) |
| 22:09:28 | <BONUS> | what does fix do |
| 22:10:16 | <dons> | recursion |
| 22:10:18 | <dons> | ?src fix |
| 22:10:35 | <dons> | lambdabot's not a happy person of late |
| 22:10:40 | <BONUS> | haha |
| 22:10:50 | <MyCatVerbs> | BONUS: fix f = f (fix f) |
| 22:10:52 | <BONUS> | i was looking for it in the 98 report but its not in there |
| 22:10:57 | <BONUS> | ah |
| 22:11:06 | <MyCatVerbs> | BONUS: builds an infinite chain of f (f (f (f (f (f... |
| 22:11:10 | <BONUS> | whats the practical use |
| 22:11:19 | <MyCatVerbs> | BONUS: none whatsoever. |
| 22:11:25 | <MedeaMelana> | That's not true |
| 22:11:29 | <MyCatVerbs> | BONUS: just another way of writing recursions. |
| 22:11:40 | <MedeaMelana> | Though don't ask me for a good example |
| 22:11:43 | <BONUS> | ah |
| 22:11:44 | <BONUS> | haha |
| 22:12:01 | <MyCatVerbs> | For example, repeat a = fix (a:), equivalent to repeat a = a : repeat a. |
| 22:12:16 | <MyCatVerbs> | Which expands to a:(a:(a:(a:(... etc. |
| 22:12:33 | <MyCatVerbs> | Twinside: I have noooo idea. That is making me scratch my head. |
| 22:12:40 | <Twinside> | yeah me too |
| 22:12:49 | <Twinside> | if I remove the type signature, it compile just fine |
| 22:13:24 | <dons> | does it assume -fglasgow-exts perhaps? |
| 22:13:36 | <Twinside> | yep |
| 22:13:45 | <Twinside> | i've got the extensions enabled |
| 22:13:58 | <BONUS> | @src filterM |
| 22:14:02 | <monochrom> | BONUS: http://www.vex.net/~trebla/haskell/fix.xhtml "you could have invented fix too" |
| 22:14:10 | <BONUS> | haha |
| 22:14:11 | <BONUS> | cool |
| 22:14:56 | <monochrom> | When you're tired of "let" and "where", and you still need recursion, consider "fix". |
| 22:16:27 | <MyCatVerbs> | :t let hork f g = f (hork g f) in hork -- I think I actually used this once, but then later came to my senses. |
| 22:16:37 | <MyCatVerbs> | Oh blast, damnation and \bot. |
| 22:16:41 | <BONUS> | lol |
| 22:17:10 | <BONUS> | haha i read the you could have invented monads too article |
| 22:17:13 | <BONUS> | and i was thinking to myself |
| 22:17:21 | <BONUS> | no way, i probably wasn't even born when they were invented wtf |
| 22:22:10 | <gwern> | BONUS: in a counterfactual universe you could have! |
| 22:22:36 | <ddarius> | BONUS: Well I believe they were first invented/discovered in the 1960s |
| 22:23:07 | <BONUS> | hm wow |
| 22:23:15 | <BONUS> | how old is haskell again? |
| 22:23:33 | <gwern> | 15 years or so |
| 22:23:59 | <BONUS> | ah well at least i'm older than haskell then |
| 22:25:24 | <BONUS> | hehe http://en.wikipedia.org/wiki/Timeline_of_programming_languages |
| 22:25:34 | <BONUS> | it looks like i'm as old as perl (1987) |
| 22:27:03 | <dons> | ACTION is going to wikify answers to any questions on the mailing list now. |
| 22:27:07 | <ddarius> | BONUS: 1987 was when Haskell first started being formulated. 1989 is when the Haskell 1.0 Report was made. |
| 22:27:46 | <BONUS> | ah |
| 22:27:47 | <BONUS> | awesome :D |
| 22:28:03 | <ddarius> | So Haskell is going on 20. |
| 22:28:04 | <gwern> | dons: a valiant goal, but google taught us that having answers is not the problem, but finding them |
| 22:28:24 | <dons> | gwern: right. refactoring will help here |
| 22:28:31 | <dons> | i think this approach has worked well for xmonad |
| 22:28:43 | <dons> | its just time and tenacity |
| 22:29:03 | <andyjgill> | Should all new packages use the Cabal 1.2 syntax for the .cabal file? |
| 22:29:16 | <andyjgill> | What is recommended? |
| 22:29:18 | <dcoutts> | andyjgill: if you want the new features, yes. |
| 22:29:38 | <andyjgill> | What are the requirements? 6.8.2+? |
| 22:29:40 | <dcoutts> | andyjgill: if your package is trivial it doesn't really matter, we're not going to kill off the old syntax any time soon |
| 22:30:16 | <dcoutts> | andyjgill: Cabal-1.2 was bundled with ghc-6.8.x if that's what you mean, one can of course install it for any version of ghc since 6.2 |
| 22:30:17 | <dons> | we've a wiki page with the old and new library deps |
| 22:30:38 | <dons> | andyjgill: http://www.haskell.org/haskellwiki/Upgrading_packages |
| 22:30:52 | <andyjgill> | great. |
| 22:31:58 | <andyjgill> | I think we'll just use cabal-1.2 syntax. It seems cleaner. Any issues to want for? |
| 22:32:50 | <andyjgill> | want=>watch |
| 22:32:57 | <dcoutts> | andyjgill: ahh :-) no, not really |
| 22:33:12 | <dons> | just checking that you get any lib dependencies correct |
| 22:33:18 | <dcoutts> | andyjgill: except that older cabal will not understand it at all (no helpful error message) |
| 22:33:29 | <andyjgill> | Thanks! |
| 22:33:50 | <dcoutts> | dons: that's upgrading ghc-6.8, not cabal |
| 22:34:00 | <andyjgill> | What is *build-type*? |
| 22:34:07 | <dcoutts> | andyjgill: usually Simple |
| 22:34:20 | <dons> | or Configure if you run a configure script |
| 22:34:27 | <dcoutts> | andyjgill: unless you need a custom Setup.hs or ./configure script |
| 22:34:42 | <andyjgill> | Ahh. okay. |
| 22:35:04 | <dcoutts> | or *shudder* make |
| 22:35:39 | <dons> | but no one is that crazy, dcoutts |
| 22:35:42 | <dcoutts> | ACTION notes that out of the 1 cabal packages on hackage that use the Make build-type, 0 get it correct |
| 22:36:04 | <dons> | heh. that's a pretty poor percent |
| 22:36:14 | <dons> | just remove the Make option? |
| 22:36:45 | <dcoutts> | it's because if you use Make you essentially have to implement your own Haskell build system from scratch |
| 22:37:07 | <dcoutts> | so you end up ignoring many of the build flags/options that users expect |
| 22:37:11 | <dons> | wow, docon is really really stressing ghc. its not allocating a lot of memory, but it is now taking 10-20 minutes per module |
| 22:37:42 | <dons> | ACTION takes this as a sign that serge has done something interesting |
| 22:37:51 | <dcoutts> | dons: wx uses it and it needs some fairly complex build stuff |
| 22:38:10 | <mm_freak> | i'd like to write an MPD frontend using Gtk2hs and Network.MPD, but i can't figure out, how to keep the connection open for the program's lifetime, while allowing it to change… should i use concurrency? |
| 22:38:33 | <dons> | mm_freak: a process handle and a reader forkIO thread would work. |
| 22:38:51 | <dons> | mm_freak: see hmp3, perhaps, which talks to mpg321 over a channel, via a concurrent thread |
| 22:39:05 | <mm_freak> | dons: i used to use Chan for such things |
| 22:39:26 | <dons> | yeah, that's a good way. you just have a reader or writer thread communicating with the main program over a lazy chan |
| 22:39:39 | <mm_freak> | ok, thanks |
| 22:39:56 | <dcoutts> | mm_freak: that's a reasonable idea, use a Chan and that way you can switch network connection without the reader end of the Chan noticing |
| 22:40:32 | <dcoutts> | mm_freak: you can just kill off the old writer that was connected to the old network channel and fire up a new one to read from the new connection and keep writing into the Chan |
| 22:41:02 | <dcoutts> | or did I misunderstand the problem? |
| 22:41:20 | <mm_freak> | yes, that was my initial idea… it's just the monadic interface to MPD, which confused me |
| 22:41:31 | <mm_freak> | i'm used to handles and functions on them |
| 22:46:10 | <mm_freak> | seeing that MPD is a MonadIO, is there a better way to do it? or is that only useful, when the main part of the program consists of MPD actions and IO is only used for some output messages? |
| 22:47:01 | <dcoutts> | mm_freak: so does MPD only handle output or also input from the network? |
| 22:47:43 | <mm_freak> | dcoutts: everything |
| 22:47:59 | <mm_freak> | inside the MPD monad, you can get song info and stuff, add songs, etc. |
| 22:48:24 | <dcoutts> | mm_freak: hmm, so how do you tell it what channel to use? |
| 22:48:38 | <dcoutts> | channel/connection whatever |
| 22:49:18 | <mm_freak> | dcoutts: using withMPDEx, which you give connection informations and an action to run on that connection |
| 22:49:31 | <mm_freak> | or using withMPD, which is a simple interface to withMPDEx |
| 22:49:45 | <dcoutts> | mm_freak: so it doesn't let you change connection later |
| 22:49:50 | <mm_freak> | yes |
| 22:50:37 | <mm_freak> | there is a 'reconnect' function, but it doesn't allow altering connection info |
| 22:50:47 | <dcoutts> | ahh |
| 22:51:03 | <dcoutts> | mm_freak: and that's exactly what you want to do? |
| 22:52:57 | <dcoutts> | mm_freak: if so, I don't see any obvious workaround, you may just have to change the MPD stuff to be more flexible with the connection handling (either just to allow better reconnects or perhaps letting you manage the input and output separately) |
| 22:53:01 | <mm_freak> | my question is whether the liftIO is useful at all |
| 22:53:32 | <mm_freak> | other than for outputting simple status messages |
| 22:54:25 | <Saizan> | mm_freak: it's useful as much as the IO monad, no? |
| 22:54:40 | <SamB> | ACTION wonders why gibbons claims that ordinary ADTs are data, not codata |
| 22:55:15 | <mm_freak> | Saizan: in the MPD monad, specifically, but i think i see that i actually need it, at least to read from the channel |
| 22:55:33 | <mm_freak> | otherwise i'd need to close the connection to do it |
| 22:56:44 | <Saizan> | yeah, that was what i meant |
| 22:57:11 | <dcoutts> | SamB: hmm? I thought he does say ADTs are codata. In the abstract and intro. |
| 22:57:36 | <SamB> | dcoutts: section 3 |
| 22:57:36 | <dcoutts> | SamB: which page are you looking at? |
| 22:58:32 | <SamB> | "as opposed to the ordinary data inhabiting the more familiar algebraic datatypes introduced by constructions such as Haskell's data declaration |
| 23:00:07 | <Philippa_> | dcoutts: algebraic datatypes are both in Haskell, but not in strict languages |
| 23:00:27 | <Philippa_> | SamB: the distinction is essentially that codata is coalgebraic |
| 23:01:07 | <dcoutts> | Philippa_: yes, and he does mention that on the following page |
| 23:01:26 | <SamB> | he "as opposed to" implies the negation of "haskell data declarations declare codata" |
| 23:01:28 | <Philippa_> | SamB: there's this "coincidence" whereby in CPO, initial algebras and final coalgebras are isomorphic |
| 23:02:26 | <Philippa_> | really it's that haskell's not an ideal choice of example language, that's all |
| 23:03:20 | <dcoutts> | SamB: he makes that point in the following paragraph |
| 23:03:51 | <SamB> | he could never get away with this in a formal proof |
| 23:04:14 | <Philippa_> | he's not presenting something formal |
| 23:04:26 | <SamB> | yes, it's easy to tell because he wrote it in english ;-) |
| 23:04:48 | <Philippa_> | no. The thing being presented with english around it /itself/ is not formal |
| 23:05:12 | <SamB> | what "thing" is that? |
| 23:05:48 | <Philippa_> | a slightly handwavy notion of 'codata', in the same sense that many people in here have a slightly handwavy notion of 'data' that makes no reference to initial algebras |
| 23:06:14 | <Philippa_> | and a similarly handwavy encoding into haskell |
| 23:06:16 | <dcoutts> | SamB: it's an illustration, haskell data is normally intended as data, not co-data |
| 23:06:42 | <Philippa_> | right. Half the point is "here is an idea, anyone else fancy playing with it?" |
| 23:06:49 | <SamB> | > cycle "orly" |
| 23:07:04 | <SamB> | where did lambdabot go??? |
| 23:07:28 | <jleedev> | @seen lambdabot |
| 23:07:32 | <SamB> | hahaha |
| 23:13:20 | <SamB> | hmm, very frustrating not being able to convert the streams back to lists :-(... |
| 23:15:54 | <dcoutts> | SamB: ? |
| 23:16:06 | <SamB> | I'm not allowed to do that |
| 23:16:13 | <ddarius> | SamB: data isn't codata, that's the nature of the beast. |
| 23:16:23 | <SamB> | since it would not have productivity guarentees |
| 23:16:34 | <SamB> | even with lists as codata |
| 23:16:48 | <dcoutts> | oh it's just because one is a bigger type than the other |
| 23:17:09 | <dcoutts> | you have to restrict yourself to the list subset of Stream |
| 23:17:31 | <dcoutts> | or at least to respecting the equivalences classes in Stream that we map to list |
| 23:18:01 | <SamB> | I don't have a clue how to convince Coq that I'm doing that ;-) |
| 23:18:20 | <dcoutts> | hmm, can you define the equivalence classes precisely? |
| 23:18:43 | <dcoutts> | so there are two problems, co-data to data |
| 23:18:50 | <SamB> | that isn't it |
| 23:18:55 | <dcoutts> | and mapping back into a type without Skip |
| 23:19:02 | <SamB> | that IS it |
| 23:19:17 | <dcoutts> | and you're working in a system without _|_ too right? |
| 23:19:25 | <SamB> | indeed |
| 23:19:27 | <ddarius> | ACTION should be able to parse anything LolliMon parses now... |
| 23:19:31 | <dcoutts> | since of course lack of progress is just _|_ |
| 23:19:54 | <dcoutts> | SamB: so you need to guarantee you're not in the pre-image of _|_ in List |
| 23:20:09 | <SamB> | I don't know how to do that either ;-) |
| 23:20:12 | <dcoutts> | there's the equivalence class in Stream that is mapped to _|_ |
| 23:20:17 | <dcoutts> | define it, prove you're not in it |
| 23:20:32 | <dcoutts> | basically no infinite sequences of Skip |
| 23:20:55 | <SamB> | yeah |
| 23:20:59 | <SamB> | hmm. |
| 23:21:15 | <SamB> | I guess that could actually help me get where I want to go. |
| 23:21:49 | <dcoutts> | so whenever you make one you have to prove that if you're using Skip that you don't keep making more |
| 23:22:13 | <SamB> | but right now I'd like to define an equality relation that I can prove all three properties for ;-) |
| 23:22:36 | <mm_freak> | @src undefined |
| 23:22:46 | <mm_freak> | @src error |
| 23:22:54 | <dolio> | undefined = error "Prelude.undefined" or something like that. |
| 23:23:02 | <mm_freak> | > "I am here" :: String |
| 23:23:07 | <dcoutts> | na, undefined = undefined :-) |
| 23:23:07 | <mm_freak> | hmm |
| 23:23:15 | <dolio> | > undefined |
| 23:23:37 | <SamB> | dolio: it looks like lambdabot decided to just not terminate this time around? |
| 23:23:40 | <SamB> | ACTION teases dolio |
| 23:23:42 | <dolio> | The error message disagrees with you, I think. :) |
| 23:23:42 | <mm_freak> | how does 'error' work? |
| 23:24:05 | <dolio> | Magic. |
| 23:24:18 | <SamB> | mm_freak: it depends on whether or not you import Control.Exception |
| 23:24:19 | <mm_freak> | certainly, but what kind of magic? unsafe magic? |
| 23:24:35 | <kadir> | hello |
| 23:24:39 | <kadir> | getSelection :: MonadIO m => m String |
| 23:24:44 | <SamB> | if you don't, it doesn't really matter... |
| 23:24:48 | <kadir> | how to get String here |
| 23:24:53 | <monochrom> | mm_freak: I think you could elaborate your question. |
| 23:24:57 | <dolio> | It's probably hard wired to the runtime system or something. Although semantically you could write it as 'error s = error s' or any number of other things. |
| 23:24:59 | <SamB> | if you do, it raises an exception ;-) |
| 23:25:20 | <mm_freak> | yes, it drops me back to the IO monad, even from pure functions |
| 23:25:25 | <mm_freak> | that's what confuses me |
| 23:25:37 | <SamB> | mm_freak: because catching it is not pure |
| 23:25:45 | <dcoutts> | mm_freak: it's wired in to the rts, in yhc it terminates the prog, in ghc it raises an exception |
| 23:26:08 | <mm_freak> | ok |
| 23:26:14 | <dcoutts> | or maybe yhc uses exceptions now, in nhc98 it terminates the prog |
| 23:26:37 | <mm_freak> | so i shouldn't assume any particular implementation in "error" |
| 23:27:13 | <dcoutts> | mm_freak: not if you can help it |
| 23:27:19 | <mm_freak> | like a bottom value for errors |
| 23:27:32 | <dcoutts> | semantically it is bottom |
| 23:27:38 | <mm_freak> | ok, thanks |
| 23:29:02 | <conal> | mm_freak: the reason error handling is handled in IO, is that the semantics of pure values (including functions) is too simple to capture exceptions. IO has intractable semantics anyway, so exceptions etc are dumped there (the "sin bin"). |
| 23:29:59 | <mm_freak> | conal, SamB: thank you, but that wasn't the source of my confusion… it's just that my understanding is that you can't throw exceptions in pure functions |
| 23:30:12 | <SamB> | mm_freak: but you can |
| 23:30:15 | <augur> | tuples are like lists right? |
| 23:30:23 | <mm_freak> | augur: no |
| 23:30:23 | <SamB> | there's nothing impure about that |
| 23:30:25 | <augur> | no? |
| 23:30:29 | <conal> | augur: yes & no |
| 23:30:32 | <SamB> | augur: only in Python |
| 23:30:34 | <augur> | well |
| 23:30:39 | <augur> | well what i mean is |
| 23:30:42 | <augur> | they can take any value |
| 23:30:45 | <newsham> | mmm python |
| 23:30:48 | <augur> | but only if they're all the same type right? |
| 23:30:52 | <mm_freak> | augur: they can be heterogenous and have a fixed length |
| 23:30:55 | <newsham> | > ("test", 23) |
| 23:30:59 | <augur> | oh i see. |
| 23:31:07 | <newsham> | ?bot |
| 23:31:09 | <lament> | augur: they're the same as tuples in math. |
| 23:31:23 | <ddarius> | Curses! |
| 23:32:31 | <kadir> | i couldn't find any way to grab String from a monadic one |
| 23:32:33 | <mm_freak> | @src throw |
| 23:32:35 | <mm_freak> | oh |
| 23:32:43 | <mm_freak> | what's wrong with lambdabot ? |
| 23:32:52 | <newsham> | ?bot temporary |
| 23:32:52 | <noBotE> | :) |
| 23:32:54 | <kadir> | could i ask for help? |
| 23:33:15 | <newsham> | kadir: you could |
| 23:33:48 | <mm_freak> | SamB: true, then it drops me back to IO, but how is 'throw' implemented? |
| 23:33:57 | <kadir> | getSelection :: MonadIO m => m String |
| 23:34:01 | <mm_freak> | does it need to use a special language feature? |
| 23:34:04 | <SamB> | mm_freak: magic! |
| 23:34:09 | <mm_freak> | ok |
| 23:34:11 | <kadir> | i want String here :) |
| 23:34:20 | <kadir> | but can't do |
| 23:34:36 | <mm_freak> | kadir: (>>=) or some monad-specific function |
| 23:34:44 | <SamB> | as in "rts functions" |
| 23:35:10 | <mm_freak> | SamB: i understand… i just thought that there is no such magic in haskell =) |
| 23:35:48 | <mm_freak> | if i wanted to write 'myThrow', would there be any way without resorting to 'throw'? |
| 23:35:57 | <SamB> | not really |
| 23:35:59 | <kadir> | i want somehow to concat another string to this string if i extract string from the function |
| 23:36:09 | <mm_freak> | ok |
| 23:36:21 | <mm_freak> | kadir: what is 'm'? |
| 23:36:29 | <kadir> | (foo $ getSelection) ++ "bar" |
| 23:36:37 | <kadir> | couldn't i do this? |
| 23:36:41 | <mm_freak> | no |
| 23:37:06 | <mm_freak> | unless foo is a function specific to a particular 'm', which removes the monad |
| 23:37:40 | <kadir> | of course i trying to write a function exactly you mention to do |
| 23:37:45 | <kadir> | but i couldn't |
| 23:38:03 | <SamB> | dcoutts: well I've found a definition which I can prove reflexivity for... |
| 23:38:16 | <kadir> | Control.Monad.Trans.MonadIO |
| 23:38:23 | <kadir> | what the 'm' is |
| 23:38:36 | <dcoutts> | SamB: sounds good |
| 23:38:53 | <mm_freak> | kadir: you can't, at that general level |
| 23:39:23 | <mm_freak> | value extraction is an optional feature for some monads… usually by some 'run' or 'eval' function |
| 23:40:25 | <SamB> | I'm defining the primitive equality in terms of a Coq equivalent of [Maybe a], since I *can* convert streams to those... |
| 23:41:08 | <kadir> | ohh :( is haskell structred on the big branch: Monad - non-Monad ? |
| 23:41:51 | <kadir> | i could'nt obtain simply a String created from a monadic function |
| 23:41:57 | <mm_freak> | kadir: no, but monads are an integral thing to haskell |
| 23:42:37 | <mm_freak> | you could, either inside of the monad, or with a special function to 'unwrap' the value |
| 23:42:54 | <mm_freak> | for example, you do it all the time inside the IO monad |
| 23:43:07 | <mm_freak> | do { args <- getArgs; print args } |
| 23:43:16 | <mm_freak> | getArgs :: IO [String] |
| 23:44:00 | <malebria> | YAHT is for people with some experience in programming, right? What would you recommend for complete begginers in programming? |
| 23:44:01 | <kadir> | but i want that args to concat with another string outside there |
| 23:44:11 | <kadir> | isn't that possbile |
| 23:45:10 | <mm_freak> | kadir: it is… inside IO =) |
| 23:45:14 | <Torment> | kadir: do { [string] <- getArgs; print (pureString ++ string) } |
| 23:45:48 | <mm_freak> | do { args <- getArgs; print (map (++ "blah") args) } |
| 23:46:21 | <kadir> | could i tell what i want to do? |
| 23:46:50 | <mm_freak> | sure, maybe that helps |
| 23:46:59 | <kadir> | i only wanted to add one usefull keybinding in xmonad |
| 23:47:11 | <kadir> | but couldn't succeed :( |
| 23:47:19 | <malebria> | Is there a page comparing GHC with other haskell interpreters/compilers? |
| 23:47:23 | <kadir> | here is keybinding |
| 23:47:31 | <kadir> | ((modMask .|. controlMask, xK_b), runInTerm "echo \"" ++ getSelection ++ "\" | vim -") |
| 23:47:38 | <ivanm> | kadir: you need to use something like M.union |
| 23:48:02 | <mm_freak> | kadir: maybe you just need to add parentheses |
| 23:48:10 | <malebria> | As I see everybody using GHC most of the time, I ask myself what are the reasons to use the others. |
| 23:48:18 | <mm_freak> | runInTerm ("echo" ++ … ) |
| 23:48:29 | <ivanm> | kadir: see how they do it here: http://code.haskell.org/XMonadContrib/XMonad/Config/Xfce.hs |
| 23:48:39 | <Jedai> | kadir: ((modMask .|. controlMask, xK_b), do { sel <- getSelection; runInTerm "echo \"" ++ sel ++ "\" | vim -") |
| 23:48:41 | <dons> | they have mainly only niche uses now, malebria |
| 23:48:51 | <Jedai> | kadir: ((modMask .|. controlMask, xK_b), do { sel <- getSelection; runInTerm "echo \"" ++ sel ++ "\" | vim -" } ) |
| 23:48:53 | <mm_freak> | malebria: you should read the homepages for the other compilers/interpreters… they usually compare themselves to GHC |
| 23:49:39 | <Jedai> | Or something like that, I'm pretty sure there's a simple way to do it anyway |
| 23:49:47 | <malebria> | I'll take a look.. |
| 23:51:55 | <kadir> | yep, it compiled :) but didn't work :( |
| 23:57:55 | <malebria> | mm_freak: this is true for nhc98, but I hugs page, I couldn't find such comparision. |
| 23:58:41 | <mm_freak> | malebria: because Hugs is one of the more frequently used interpreters… people 'just know' the differences, but maybe the FAQ tells you |
| 23:59:13 | <ddarius> | Parsing D ::= G -o D | D o- G | ... and G ::= D -o G | G o- D | ... where D \subset G is tricky. |
| 23:59:49 | <ddarius> | ACTION should probably just postprocess it. |
Back to channel and daily index: content-negotiated html turtle