RE: [Haskell-cafe] Can we do better than duplicate APIs? [was: Data.CompactString 0.3]
[Probably [EMAIL PROTECTED] is the right list for this message, so I'm fwding your message below, and will reply there.] | -Original Message- | From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] On Behalf Of Benjamin | Franksen | Sent: 23 March 2007 22:56 | To: haskell-cafe@haskell.org | Cc: haskell@haskell.org | Subject: [Haskell-cafe] Can we do better than duplicate APIs? [was: Data.CompactString 0.3] | | [sorry for the somewhat longer rant, you may want to skip to the more | technical questions at the end of the post] | | Twan van Laarhoven wrote: | I would like to announce version 0.3 of my Data.CompactString library. | Data.CompactString is a wrapper around Data.ByteString that represents a | Unicode string. This new version supports different encodings, as can be | seen from the data type: | | [...] | | Homepage: http://twan.home.fmf.nl/compact-string/ | Haddock: http://twan.home.fmf.nl/compact-string/doc/html/ | Source:darcs get http://twan.home.fmf.nl/repos/compact-string | | After taking a look at the Haddock docs, I was impressed by the amount of | repetition in the APIs. Not ony does Data.CompactString duplicate the whole | Data.ByteString interface (~100 functions, adding some more for encoding | and decoding), the whole interface is again repeated another four times, | once for each supported encoding. | | Now, this is /not/ meant as a criticism of the compact-string package in | particular. To the contrary, duplicating a fat interface for almost | identical functionality is apparently state-of-the-art in Haskell library | design, viz. the celebrated Data.Bytesting, whose API is similarly | repetitive (see Data.List, Data.ByteString.Lazy, etc...), as well as | Map/IntMap/SetIntSet etc. I greatly appreciate the effort that went into | these libraries, and admire the elegance of the implementation as well as | the stunning results wrt. efficiency gains etc.. However I fear that | duplicating interfaces in this way will prove to be problematic in the long | run. | | The problems I (for-)see are for maintenance and usability, both of which | are of course two sides of the same coin. For the library implementer, | maintenance will become more difficult, as ever more of such 'almost equal' | interfaces must be maintained and kept in sync. One could use code | generation or macro expansion to alleviate this, but IMO the necessity to | use extra-language pre-processors points to a weakness in the language; it | be much less complicated and more satisfying to use a language feature that | avoids the repetition instead of generating code to facilitate it. On the | other side of teh coin, usability suffers as one has to lookup the (almost) | same function in more and more different (but 'almost equal') module | interfaces, depending on whether the string in question is Char vs. Byte, | strict vs. lazy, packed vs. unpacked, encoded in X or Y or Z..., especially | since there is no guarantee that the function is /really/ spelled the same | everywhere and also really does what the user expects.(*) | | I am certain that most, if not all, people involved with these new libraries | are well aware of these infelicities. Of course, type classes come to mind | as a possible solution. However, something seems to prevent developers from | using them to capture e.g. a common String or ListLike interface. Whatever | this 'something' is, I think it should be discussed and addressed, before | the number of 'almost equal' APIs becomes unmanageable for users and | maintainers. | | Here are some raw ideas: | | One reason why I think type classes have not (yet) been used to reduce the | amount of API repetition is that Haskell doesn't (directly) support | abstraction over type constraints nor over the number of type parameters | (polykinded types?). Often such 'almost equal' module APIs differ in | exactly these aspects, i.e. one has an additional type parameter, while yet | another one needs slightly different or additional constraints on certain | types. Oleg K. has shown that some if these limitations can be overcome w/o | changing or adding features to the language, however these tricks are not | easy to learn and apply. | | Another problem is the engineering question of how much to put into the | class proper: there is a tension between keeping the class as simple as | possible (few methods, many parametric functions) for maximum usability vs. | making it large (many methods, less parametric functions) for maximum | efficiency via specialized implementations. It is often hard to decide this | question up front, i.e. before enough instances are available. (This has | been stated as a cause for defering the decision for a common interface to | list-like values or strings). Since the type of a function doesn't reveal | whether it is a normal function with a class constraint or a real class | method, I imagine a language feature that (somehow) enables me to | specialize such a function for a
RE: [Haskell-cafe] What ever happened to Haskell 98 as a stable branch?
| Why, then, are we so paranoid about introducing breaking changes in | the development branch of haskell? Why are we stuck without the class | system extension proposal? Why is Num so still so horribly mangled? | Why can I not 'map' over a Set? Why must I use lists of characters if | I desire standard sorting? Why can I not get a good error message | from read? It's not paranoia about breaking changes. It's simply because no one has done it. Haskell is rather a Darwinian sort of place. The way lies entirely open for you to make an alternative Prelude that is just as you want it to be. Even H98 allows you to say import Prelude () to kill the Prelude, but GHC's -fno-implicit-prelude flag goes further in supporting alternative Preludes (see the docs). OK, say you do this. If your setup is sufficiently compelling, people will use it. Yes, they will have to add a one-line pragma to the top of their modules, but as Alex has been arguing in another thread this weekend, it is no bad thing for a module to advertise the language in which it is written. I don't think that one line would be a sufficient discouragement if your Prelude offered real advantages. And Cabal makes it easy for people to download and build your library. But building a well-engineered library, or set of libraries, is a lot of work. That's the problem, not paranoia. So you don't have to persuade some committee that you are right; you can just go do it. And that would be a great way to contribute. Simon PS: The same goes for this suggestion | [Conjecture 1 (2007). Haskell Mathematical Prelude and Mathematicians] If | Haskell had a mathematically sound prelude then more mathematicians would | use Haskell. A mathematically sound Prelude would be great. Go for it! ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] AI Strike Force!
Andrew Wagner wrote: The time has come! Calling all Haskell programmers interested in AI! I've established a new home base at http://www.haskell.org/haskellwiki/AI . I have added a link to the Google Summer of Code ticket for a machine learning library, which I hope is approriate to categorize as AI. While the library was my suggestion (and I'm prepared to spend the summer on this project) I'm very interested in having other people support this as (co-)mentors -- there's already quite a bit of student interest. The SoC projects tend to gravitate towards develop towards development tools, but with sufficient interest from the community, it should be possible to get a slot for more domain specific stuff -- especially as this is a very broad domain. -k ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] A question about functional dependencies and existential quantification
Hi, I am trying to do something like the following: {-# OPTIONS -fglasgow-exts -fallow-undecidable-instances #-} module TestCase where data Any root = forall pos sel . T root pos sel = ANY pos class T root pos sel | pos - root, root - sel where f :: pos - sel - Bool instance T root (Any root) sel where f (ANY p) s = f p s There is a multi-parameter type class T with some functional dependencies. And I want do define an almost general type for T, Any root. I would like to have that type in T as well. But ghc is not able to type check f. It gives: TestCase.hs:10:7: Couldn't match expected type `sel1' (a rigid variable) against inferred type `sel' (a rigid variable) `sel1' is bound by the pattern for `ANY' at TestCase.hs:10:7-11 `sel' is bound by the instance declaration at TestCase.hs:9:0 When using functional dependencies to combine T root pos sel, arising from use of `f' at TestCase.hs:10:18-22 T root pos sel1, arising from is bound by the pattern for `ANY' at TestCase.hs:10:7-11 at TestCase.hs:10:7-11 In the pattern: ANY p In the definition of `f': f (ANY p) s = f p s I think sel1 and sel are equal, because the root in the type of (ANY p) on the left side is the same as the root of the type of f p s on the right side. From that should follow with help of the functional dependency that sel1 and sel are the same types. Do I misunderstand the type system or is that a weakness of GHC? Or am I trying to do something silly? I have a solution that involves requiring sel to be in Typeable and using cast and I never came across a runtime error, so far. Is there a better way to express that? Any enlightenment is appreciated. Regards, Jean-Marie ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
RE: [Haskell-cafe] A question about functional dependencies and existential quantification
What you want to do is perfectly reasonable -- but it cannot be translated into System F and that's why GHC rejects it. GHC now has a richer intermediate language that *can* handle this; see our paper http://research.microsoft.com/~simonpj/papers/ext-f. Manuel and Martin and I are now working on the *source*-language aspects, incl type inference. When we are done, we'll be able to compile your program, or at least one very like it. So, stay tuned. Meanwhile thank you for the example. Simon | -Original Message- | From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] On Behalf Of Jean- | Marie Gaillourdet | Sent: 26 March 2007 10:53 | To: haskell-cafe@haskell.org | Subject: [Haskell-cafe] A question about functional dependencies and existential quantification | | Hi, | | I am trying to do something like the following: | | {-# OPTIONS -fglasgow-exts -fallow-undecidable-instances #-} | module TestCase where | | data Any root = forall pos sel . T root pos sel = ANY pos | | class T root pos sel | pos - root, root - sel where | f :: pos - sel - Bool | | instance T root (Any root) sel where | f (ANY p) s = f p s | | There is a multi-parameter type class T with some functional | dependencies. And I want do define an almost general type for T, Any | root. I would like to have that type in T as well. But ghc is not able | to type check f. It gives: | | TestCase.hs:10:7: | Couldn't match expected type `sel1' (a rigid variable) | against inferred type `sel' (a rigid variable) |`sel1' is bound by the pattern for `ANY' at TestCase.hs:10:7-11 |`sel' is bound by the instance declaration at TestCase.hs:9:0 | When using functional dependencies to combine |T root pos sel, arising from use of `f' at TestCase.hs:10:18-22 |T root pos sel1, | arising from is bound by the pattern for `ANY' | at TestCase.hs:10:7-11 | at TestCase.hs:10:7-11 | In the pattern: ANY p | In the definition of `f': f (ANY p) s = f p s | | I think sel1 and sel are equal, because the root in the type of (ANY | p) on the left side is the same as the root of the type of f p s on | the right side. From that should follow with help of the functional | dependency that sel1 and sel are the same types. Do I misunderstand the | type system or is that a weakness of GHC? Or am I trying to do something | silly? | | I have a solution that involves requiring sel to be in Typeable and | using cast and I never came across a runtime error, so far. Is there a | better way to express that? | | Any enlightenment is appreciated. | | Regards, | Jean-Marie | | | | ___ | Haskell-Cafe mailing list | Haskell-Cafe@haskell.org | http://www.haskell.org/mailman/listinfo/haskell-cafe ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] What ever happened to Haskell 98 as a stable branch?
On Mon, 26 Mar 2007 09:20:59 +0100 Simon Peyton-Jones [EMAIL PROTECTED] wrote: | [Conjecture 1 (2007). Haskell Mathematical Prelude and Mathematicians] If | Haskell had a mathematically sound prelude then more mathematicians would | use Haskell. A mathematically sound Prelude would be great. Go for it! Unfortunately, we currently do not possess all the operations that mathematicians like to perform when making up new structures. In particular I can think of quotient types, which just causes a world of pain when it comes to decently implementing them. Sometimes, you can implement something that acts as that type (e.g. Set ~== List/Eq), but sometimes it's just not possible (Monad Product -- I can't remember what that paper was called now...) Gen signature.asc Description: PGP signature ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] A question about functional dependencies and existential quantification
Hi, thanks for your quick answer. Do you have any predictions when System F_c in GHC will be available for usage? Regards, Jean-Marie Simon Peyton-Jones wrote: What you want to do is perfectly reasonable -- but it cannot be translated into System F and that's why GHC rejects it. GHC now has a richer intermediate language that *can* handle this; see our paper http://research.microsoft.com/~simonpj/papers/ext-f. Manuel and Martin and I are now working on the *source*-language aspects, incl type inference. When we are done, we'll be able to compile your program, or at least one very like it. So, stay tuned. Meanwhile thank you for the example. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
Haskell is rather a Darwinian sort of place. With whole respect. You need two components for evolution to work: the survival of the fitness and Generator Of Diversity (GOD). Now, Haskell attracts originality and easily accommodates changes but nobody burns tires in testing anything so that complexity and learning curve grow while deficiencies remain dormant. Recent threads are a kind of healthy evolutionary pressure (survival of the fitness), but you insist that Haskell should be committed to GOD;-) With great respect, -Andrzej ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
-Ursprüngliche Nachricht- Von: Andrzej Jaworski [EMAIL PROTECTED] Gesendet: 26.03.07 15:00:47 An: Simon Peyton-Jones [EMAIL PROTECTED] CC: Haskell-Cafe@haskell.org Betreff: Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch? Haskell is rather a Darwinian sort of place. With whole respect. You need two components for evolution to work: the survival of the fitness and Generator Of Diversity (GOD). Diversity is generated by mutations. Go ahead, be mutagenous. And don't worry about theology, Simon's not GOD's prophet, he's (both of them, actually) just a doctor venerabilis. Now, Haskell attracts originality and easily accommodates changes but nobody burns tires in testing anything so that complexity and learning curve grow while deficiencies remain dormant. Recent threads are a kind of healthy evolutionary pressure (survival of the fitness), but you insist that Haskell should be committed to GOD;-) With great respect, -Andrzej With TIC, Daniel ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
RE: [Haskell-cafe] A question about functional dependencies and existential quantification
| thanks for your quick answer. Do you have any predictions when System | F_c in GHC will be available for usage? Somewhere between 2 and 4 months is my guess Simon ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] Newbie: a parser for a list of objects?
Please see my questions inside comments {-- --} : Thanks! --- module Parser where import Data.Char type Parse a b = [a] - [(b, [a])] {-- Newbie: a parser for a list of objects? I am working with the section 17.5 Case study: parsing expressions of the book Haskell The Craft of Functional Programming, where a parser for a list of objects is defined. I called this function pList in order to avoid confusion with 'list' as a term for data structure. Please help me to understand how pList works (please, see the rest of the code at the end of this message): --} pList :: Parse a b - Parse a [b] pList p = (succeed []) `alt` ((p * pList p) `build` (uncurry (:))) {-- First of all, I don't quite understand why there must be a choice ('alt') between the function ('succeed') that always returns an empty list and the other part? This results in adding [] to the front, why? I thought that 'simplified' version of pList should still work fine. Trying to prove this I wrote : --} pL1 :: Parse a b - Parse a [b] pL1 p = (p * pL1 p) `build` (uncurry (:)) {-- Which, as expected, does not work correctly - just gives an empty list [] - but I don't understand why: *Parser t1 12345 [] *Parser Also, I don't understand why the textbook version of pList gives this result: *Parser test 12345 [(,12345),(1,2345),(12,345),(123,45),(1234,5),(12345,)] *Parser In particular, I don't understand where the first element (,12345) of the resulting list comes from? I am trying to figure out how pList recursively unfolds. To my mind operators in the expression: (succeed []) `alt`((p * pList p) `build` (uncurry (:))) has the following execution order: 1) * 2) 'build' 3) 'alt' It seems that operation * should be done as many times as many elements the input list has. Right? Signature: (*) :: Parse a b - Parse a c - Parse a (b, c) implies that second argument of the expression: p * pList p should be of type 'Parse a c' but in this application it is of type 'Parse a b - Parse a [b]' How can that be? How recursion termination conditinon is expressed in pList? --} none :: Parse a b none inp = [] succeed :: b - Parse a b succeed val inp = [(val, inp)] suc:: b - [a] - [(b, [a])] suc val inp = [(val, inp)] spot :: (a - Bool) - Parse a a spot p [] = [] spot p (x:xs) | p x = [(x, xs)] | otherwise = [] alt :: Parse a b - Parse a b - Parse a b alt p1 p2 inp = p1 inp ++ p2 inp bracket = spot (=='(') dash = spot (== '-') dig = spot isDigit alpha = spot isAlpha infixr 5 * (*) :: Parse a b - Parse a c - Parse a (b, c) (*) p1 p2 inp = [((x,y), rem2) |(x, rem1) - p1 inp, (y, rem2) - p2 rem1] build :: Parse a b - (b - c) - Parse a c build p f inp = [ (f x, rem) | (x, rem) - p inp] test = pList dig t1 = pL1 dig ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
RE: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
I didn't understand what you meant, so I'll withdraw the Darwinian analogy. All I mean is: if you think the Prelude is inadequate, an excellent strategy is to write a better one. If it's better, people may start to use it, and your good ideas will spread. Simon | -Original Message- | From: Andrzej Jaworski [mailto:[EMAIL PROTECTED] | Sent: 26 March 2007 14:02 | To: Simon Peyton-Jones | Cc: Haskell-Cafe@haskell.org | Subject: Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch? | | Haskell is rather a Darwinian sort of place. | | With whole respect. You need two components for evolution to work: the | survival of the fitness and Generator Of Diversity (GOD). | | Now, Haskell attracts originality and easily accommodates changes but nobody | burns tires in testing anything so that complexity and learning curve grow | while deficiencies remain dormant. | | Recent threads are a kind of healthy evolutionary pressure (survival of the | fitness), but you insist that Haskell should be committed to GOD;-) | | With great respect, | -Andrzej ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] Lazy parser with parsec.
I'm trying to figure out how to write a simple parser in Parsec to tokenize a subset of RTF. The problem is that I haven't been able to come up with a way of writing the parser that doesn't try consuming all of the input just to return the first token. The 'many' primitive's implementation uses an accumulator, and obviously has to parse to the end. Trying to iterate myself causes stack overflows on large inputs. Does anyone know of any existing Parser parsers that don't consume their entire input, or am I probably best off making my own parser. Thanks, David ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
Daniel Fischer has cared to inform me that: Diversity is generated by mutations. With due respect, but this is hardly a revelation. My point was that you need two competing components in relative balance to grow something meaningful. Cancer growth is based solely on mutation! Also I was not theological. It is the advice to multiply Prelude and use time to verify them rather cosmic in scale. It implies the assumption that the world will freeze and wait for the verdict. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] Newbie: a parser for a list of objects?
-Ursprüngliche Nachricht- Von: Dmitri O.Kondratiev [EMAIL PROTECTED] Gesendet: 26.03.07 16:44:12 An: haskell-cafe@haskell.org Betreff: [Haskell-cafe] Newbie: a parser for a list of objects? Please see my questions inside comments {-- --} : Thanks! --- module Parser where import Data.Char type Parse a b = [a] - [(b, [a])] {-- Newbie: a parser for a list of objects? I am working with the section 17.5 Case study: parsing expressions of the book Haskell The Craft of Functional Programming, where a parser for a list of objects is defined. I called this function pList in order to avoid confusion with 'list' as a term for data structure. Please help me to understand how pList works (please, see the rest of the code at the end of this message): --} pList :: Parse a b - Parse a [b] pList p = (succeed []) `alt` ((p * pList p) `build` (uncurry (:))) {-- First of all, I don't quite understand why there must be a choice ('alt') between the function ('succeed') that always returns an empty list and the other part? This results in adding [] to the front, why? Well, if the parser p doesn't succeed, we don't want the whole thing to fail. And p will (almost certainly) fail when the end of input is reached. So without the alternative 'succeed []', we'd get pL1 dig 12 = [(('1':y),rem) | (y,rem) - pL1 dig 2] = [(('1':y),rem) | (y,rem) - [(('2':z),rem2) | (z,rem2) - pL1 dig ]] = [(('1':y),rem) | (y,rem) - [(('2':z),rem2) | (z,rem2) - []] = [(('1':y),rem) | (y,rem) - []] = [] because dig = [] I thought that 'simplified' version of pList should still work fine. Trying to prove this I wrote : --} pL1 :: Parse a b - Parse a [b] pL1 p = (p * pL1 p) `build` (uncurry (:)) {-- Which, as expected, does not work correctly - just gives an empty list [] - but I don't understand why: because the parser eventually fails when the end of input is reached. *Parser t1 12345 [] *Parser Also, I don't understand why the textbook version of pList gives this result: *Parser test 12345 [(,12345),(1,2345),(12,345),(123,45),(1234,5),(12345,)] That's because of the order of alt's arguments: (succeed [] `alt` p) inp = [([],inp)] ++ (p inp) with pList p = ((p * pList p) `build` (uncurry (:))) `alt` succeed [] the resulting list woulde be reversed. *Parser In particular, I don't understand where the first element (,12345) of the resulting list comes from? I am trying to figure out how pList recursively unfolds. To my mind operators in the expression: (succeed []) `alt`((p * pList p) `build` (uncurry (:))) has the following execution order: 1) * 2) 'build' 3) 'alt' No, the first argument of alt gets evaluated first, because (p1 `alt` p2) inp = (p1 inp) ++ (p2 inp), thus we need p1 inp first. Then we see we haven't hit bottom, so we need the second argument of (++) (resp. alt). So next we need to evaluate p, then pList p, combine the results of those with the second argument of build, uncurry (:). It seems that operation * should be done as many times as many elements the input list has. Right? Unfortunately not. Let's stay with pList dig. Say your input starts with n digits. From the example above you can conjecture that length (pList dig inp) == (n+1). Now in the outermost (dig * pList dig) branch, you apply (pList dig) to an input beginning with (n-1) digits, returning a list of length n, to each element of this list you adjoin the first digit, resulting in n + (n-1) + ... + 1 = n*(n+1)/2 applications of (*). (Lesson: you need an exclusive choice, using the second parser only if the first one fails and a maximal munch combinator in your library, too) Signature: (*) :: Parse a b - Parse a c - Parse a (b, c) implies that second argument of the expression: p * pList p should be of type 'Parse a c' but in this application it is of type 'Parse a b - Parse a [b]' c is [b], so p * pList p has type Parse a (b,[b]), then (p * pList p) `build` (uncurry (:)) has type Parse a [b] How can that be? How recursion termination conditinon is expressed in pList? recursion terminates when p fails. HTH, Daniel --} none :: Parse a b none inp = [] succeed :: b - Parse a b succeed val inp = [(val, inp)] suc:: b - [a] - [(b, [a])] suc val inp = [(val, inp)] spot :: (a - Bool) - Parse a a spot p [] = [] spot p (x:xs) | p x = [(x, xs)] | otherwise = [] alt :: Parse a b - Parse a b - Parse a b alt p1 p2 inp = p1 inp ++ p2 inp bracket = spot (=='(') dash = spot (== '-') dig = spot isDigit alpha = spot isAlpha infixr 5 * (*) :: Parse a b - Parse a c - Parse a (b, c) (*) p1 p2 inp = [((x,y), rem2) |(x, rem1) - p1 inp, (y, rem2) - p2 rem1] build :: Parse a b - (b - c) - Parse a c build p f inp = [ (f x, rem) | (x, rem) - p inp] test = pList dig t1 = pL1 dig
Re: [Haskell-cafe] Lazy parser with parsec.
David Brown [EMAIL PROTECTED] wrote: Does anyone know of any existing Parser parsers that don't consume their entire input, or am I probably best off making my own parser. http://www.cs.york.ac.uk/fp/polyparse In particular, the module Text.ParserCombinators.PolyLazy. Regards, Malcolm ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
-Ursprüngliche Nachricht- Von: Andrzej Jaworski [EMAIL PROTECTED] Gesendet: 26.03.07 18:34:00 An: [EMAIL PROTECTED] Betreff: Re: [Haskell-cafe] What ever happened to Haskell 98 as a stablebranch? Hi, I apologize for mistakenly resending my answer to two lists. Well, I can understand Simon, he has little choice but to press on, but you have healthy distance and much wider intellectual angle to see that Haskell is doomed if new features will come up without any incentive to prune the tree. Agreed. (Though I'm not sure about doomed, after all: Jeszcze Polska ... ) And having thought more about it, I'm less optimistic that better alternatives will let their predecessors wither fast enough. But perhaps we could keep the older tree until the new one bears fruit? And I also support the move for a smaller Prelude, only I don't know what to move to Data.Whatever (I strongly dislike the idea of abandoning the Prelude altogether, but I could live with[out] it). Cheers, -Andrew Cheers, Daniel ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] What ever happened to Haskell 98 as a stablebranch?
Accidentally sent to haskell@haskell.org instead of the cafe: Diversity is generated by mutations. This is hardly a revelation. It was, looong ago. My point was that you need two competing components in relative balance to grow something meaningful. And I'd think the Haskell community could take the part of 'Selektionsdruck' (don't know the correct english term). But you have a good point below, might be too slow for our short lives :( Cancer growth is based solely on mutation! Also I was not theological. Didn't think you seriously were, but you introduced the acronym, was too tempting. It is the advice to multiply Prelude and use time to verify them rather cosmic in scale. It implies the assumption that the world will freeze and wait for the verdict. Cheers, Daniel ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] Re: Lazy parser with parsec.
David Brown [EMAIL PROTECTED] writes: Does anyone know of any existing Parser parsers that don't consume their entire input, or am I probably best off making my own parser. Thomas Zielonka published his Parsec combinator lazyMany on this list a couple of times, Google for it. Here is my application of his idea: lazyMany :: Parser a - SourceName - String - [a] lazyManyp filename contents = lm state0 where Right state0 = parse getParserState filename contents -- get an initial state lm state = either (error . show) id (parse p' ) where p' = setParserState state choice [eof return [], do x - p state' - getParserState return (x:lm state')] -- Feri. ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] Re: Can we do better than duplicate APIs? [was: Data.CompactString 0.3]
Jean-Philippe Bernardy wrote: Please look at http://darcs.haskell.org/packages/collections/doc/html/Data-Collections.html for an effort to make most common operation on bulk types fit in a single framework. The last time I looked at this (shortly after you started the project) I wasn't sure if I would want to use it. Now it seems like an oasis in a desert to me. I am pretty much impressed, for instance, you managed to unify all the nine existing 'filter' types into a common type class. Cool. The only hair in the (otherwise very tasty) soup is Portability: MPTC, FD, undecidable instances which doesn't sound like it is going to replace the Prelude any time soon ;-) Never mind: I definitely consider using this instead of importing all these different Data.XYZ modules directly (and, heaven forbid, having to import them qualified whenever I need two of them in the same module). Do you forsee any particular obstacle to an integration (=providing the appropriate instances) of e.g. CompactStrings? I would even try to do this myself, as an exercise of sorts. How difficult is it in practice to work with 'undecidable instances'? Are there special traps one has to be careful to walk around? Also, we expect indexed types to solve, or at least alleviate, some problems you mention in your rant. http://haskell.org/haskellwiki/GHC/Indexed_types I have been hoping for that to resolve (some of) our troubles, but have been confused by the all the back and forth among the experts about whether they offer more, or less, or the same, as MPTCs+fundeps+whatever (and that they will probably not go into Haskell'). BTW, any reason I didn't find your collections library in the HackageDB (other than stupidity on my part)? (Just interested, I already found the darcs repo.) Cheers Ben PS: Since I read and post to the Haskell lists via gmane and a news client: Do mail clients usually respect the follow-up header, such as I insert when cross-posting, so as to restrict follow-ups to the intended list? ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] Re: Lazy parser with parsec.
Wagner Ferenc wrote: David Brown [EMAIL PROTECTED] writes: Does anyone know of any existing Parser parsers that don't consume their entire input, or am I probably best off making my own parser. Thomas Zielonka published his Parsec combinator lazyMany on this list a couple of times, Google for it. Here is my application of his idea: lazyMany :: Parser a - SourceName - String - [a] Excellent, exactly what I was looking for. Thanks, David Brown ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe
[Haskell-cafe] A question about functional dependencies and existential quantification
Jean-Marie Gaillourdet wrote I am trying to do something like the following: {-# OPTIONS -fglasgow-exts -fallow-undecidable-instances #-} module TestCase where data Any root = forall pos sel . T root pos sel = ANY pos class T root pos sel | pos - root, root - sel where f :: pos - sel - Bool instance T root (Any root) sel where f (ANY p) s = f p s The code as posted seems to have a problem. The problem is noted by GHC 6.4 and hugs but is accepted by GHC 6.6. Such a change in GHC seems strange. The problem is not related to existentials, so we just drop them {-# OPTIONS -fglasgow-exts -fallow-undecidable-instances #-} module TestCase where data Any root = ANY class T root pos sel | pos - root, root - sel where f :: pos - sel - Bool instance T root (Any root) sel test x = f ANY x Hugs and GHC 6.4 both complain about the instance of T: Hush (September 2006 version) says ERROR /tmp/j.hs:9 - Instance is more general than a dependency allows and GHC 6.4.2 says Illegal instance declaration for `T root (Any root) sel' (the instance types do not agree with the functional dependencies of the class) In the instance declaration for `T root (Any root) sel' I concur. The class declares T as being a ternary relation such that the following holds forall r p p' s s'. T(r,p,s) T(r,p',s') - s = s' Now, the instance `T root (Any root) sel' is satisfied when root=Int, sel = Bool and when root=Int, sel = Int. Does it not? That falsifies the above proposition. In other words, the instance T is not functional with respect to the first and the third arguments. That is not surprising. What is surprising is why GHC 6.6 accepts such an instance? ___ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe