From simon.jakobi at googlemail.com Wed Jun 1 00:55:58 2016 From: simon.jakobi at googlemail.com (Simon Jakobi) Date: Wed, 1 Jun 2016 02:55:58 +0200 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: There are several packages that define typeclasses for containers and, in particular, "map-like" things: * keys (no construction, no insertion) * Data.Containers from the mono-traversable package * EdisonAPI * https://github.com/commercialhaskell/jump (still in the works) Another somewhat related package is focus, which defines a common abstraction for various operations on a key-value pair in a map. From tonymorris at gmail.com Wed Jun 1 05:14:38 2016 From: tonymorris at gmail.com (Tony Morris) Date: Wed, 1 Jun 2016 15:14:38 +1000 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: Map and Set are not. On 01/06/2016 8:57 AM, "Jeffrey Brown" wrote: > In Haskell typeclasses are based on what you want to do with something. > If, for instance, you want to be able to map over a container, you can make > it an instance of class Functor -- which all the standard containers (List, > Map, Set, Tree, Maybe ...) already are. > > On Tue, May 31, 2016 at 3:26 PM, Silent Leaf > wrote: > >> In fact it all comes down to trying to add partially a feature absent >> from the Haskell language, which is the ability to distinguish values both >> on name *and* on type --thus allowing two variables of the same name if >> they have different types. >> Honestly i don't see the drawback of that name system, but i guess there >> must be one otherwise it'd have been chosen by default instead of the >> typeblind current name system. >> >> >> Le mercredi 1 juin 2016, Silent Leaf a ?crit : >> > All in the title. I haven't used them much, but I saw Map or Vector >> types were forcing the user to use qualified functions unless you want >> nameclash with the more basic, typically list-oriented functions. >> > So, why not have a massive, general purpose interface so the type only >> can separate between containers --which would allow for cross-container >> polymorphism, i suppose, more easily, even though it's not necessarily the >> most widespread need. >> > So, do i miss something? Is there in fact a class of that kind? If so >> why not? >> > Thanks in advance! :) >> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >> >> > > > -- > Jeffrey Benjamin Brown > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From rpglover64 at gmail.com Wed Jun 1 16:35:48 2016 From: rpglover64 at gmail.com (Alex Rozenshteyn) Date: Wed, 01 Jun 2016 16:35:48 +0000 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: Map is (you map over the values, not the keys). On Wed, Jun 1, 2016 at 1:14 AM Tony Morris wrote: > Map and Set are not. > On 01/06/2016 8:57 AM, "Jeffrey Brown" wrote: > >> In Haskell typeclasses are based on what you want to do with something. >> If, for instance, you want to be able to map over a container, you can make >> it an instance of class Functor -- which all the standard containers (List, >> Map, Set, Tree, Maybe ...) already are. >> >> On Tue, May 31, 2016 at 3:26 PM, Silent Leaf >> wrote: >> >>> In fact it all comes down to trying to add partially a feature absent >>> from the Haskell language, which is the ability to distinguish values both >>> on name *and* on type --thus allowing two variables of the same name if >>> they have different types. >>> Honestly i don't see the drawback of that name system, but i guess there >>> must be one otherwise it'd have been chosen by default instead of the >>> typeblind current name system. >>> >>> >>> Le mercredi 1 juin 2016, Silent Leaf a ?crit : >>> > All in the title. I haven't used them much, but I saw Map or Vector >>> types were forcing the user to use qualified functions unless you want >>> nameclash with the more basic, typically list-oriented functions. >>> > So, why not have a massive, general purpose interface so the type only >>> can separate between containers --which would allow for cross-container >>> polymorphism, i suppose, more easily, even though it's not necessarily the >>> most widespread need. >>> > So, do i miss something? Is there in fact a class of that kind? If so >>> why not? >>> > Thanks in advance! :) >>> >>> _______________________________________________ >>> Beginners mailing list >>> Beginners at haskell.org >>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >>> >>> >> >> >> -- >> Jeffrey Benjamin Brown >> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >> >> _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From silent.leaf0 at gmail.com Wed Jun 1 17:18:56 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Wed, 1 Jun 2016 19:18:56 +0200 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: map and set are not what? I didn't get it. That's cool, I'll look into it! As for why Haskell doesn't allow natural overloading of any function name merely by choosing another name, does anyone know? Le mercredi 1 juin 2016, Alex Rozenshteyn a ?crit : > Map is (you map over the values, not the keys). > > On Wed, Jun 1, 2016 at 1:14 AM Tony Morris wrote: >> >> Map and Set are not. >> >> On 01/06/2016 8:57 AM, "Jeffrey Brown" wrote: >>> >>> In Haskell typeclasses are based on what you want to do with something. If, for instance, you want to be able to map over a container, you can make it an instance of class Functor -- which all the standard containers (List, Map, Set, Tree, Maybe ...) already are. >>> On Tue, May 31, 2016 at 3:26 PM, Silent Leaf wrote: >>>> >>>> In fact it all comes down to trying to add partially a feature absent from the Haskell language, which is the ability to distinguish values both on name *and* on type --thus allowing two variables of the same name if they have different types. >>>> Honestly i don't see the drawback of that name system, but i guess there must be one otherwise it'd have been chosen by default instead of the typeblind current name system. >>>> >>>> Le mercredi 1 juin 2016, Silent Leaf a ?crit : >>>> > All in the title. I haven't used them much, but I saw Map or Vector types were forcing the user to use qualified functions unless you want nameclash with the more basic, typically list-oriented functions. >>>> > So, why not have a massive, general purpose interface so the type only can separate between containers --which would allow for cross-container polymorphism, i suppose, more easily, even though it's not necessarily the most widespread need. >>>> > So, do i miss something? Is there in fact a class of that kind? If so why not? >>>> > Thanks in advance! :) >>>> _______________________________________________ >>>> Beginners mailing list >>>> Beginners at haskell.org >>>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >>>> >>> >>> >>> >>> -- >>> Jeffrey Benjamin Brown >>> _______________________________________________ >>> Beginners mailing list >>> Beginners at haskell.org >>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >>> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From silent.leaf0 at gmail.com Wed Jun 1 17:39:31 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Wed, 1 Jun 2016 19:39:31 +0200 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: I happen to have gotten my answer somewhere else (as for why values aren't overloadable as soon as you change the type of it). Indeed it does seem very useful to control name overloading by using typeclasses, which aside from grouping several overloadable variables together (so they can always use each other without fearing for the instance for say "mempty" wouldn't have been made when the one for "mappend" would have been), has the advantage to force the overloading instances to obey to some pattern (instead of accepting a (+) value which, say, does the same than (!!)) given in advance, especially they are parameterized over only one type (barring use of some extensions of the language). Le mercredi 1 juin 2016, Alex Rozenshteyn a ?crit : > Map is (you map over the values, not the keys). > > On Wed, Jun 1, 2016 at 1:14 AM Tony Morris wrote: >> >> Map and Set are not. >> >> On 01/06/2016 8:57 AM, "Jeffrey Brown" wrote: >>> >>> In Haskell typeclasses are based on what you want to do with something. If, for instance, you want to be able to map over a container, you can make it an instance of class Functor -- which all the standard containers (List, Map, Set, Tree, Maybe ...) already are. >>> On Tue, May 31, 2016 at 3:26 PM, Silent Leaf wrote: >>>> >>>> In fact it all comes down to trying to add partially a feature absent from the Haskell language, which is the ability to distinguish values both on name *and* on type --thus allowing two variables of the same name if they have different types. >>>> Honestly i don't see the drawback of that name system, but i guess there must be one otherwise it'd have been chosen by default instead of the typeblind current name system. >>>> >>>> Le mercredi 1 juin 2016, Silent Leaf a ?crit : >>>> > All in the title. I haven't used them much, but I saw Map or Vector types were forcing the user to use qualified functions unless you want nameclash with the more basic, typically list-oriented functions. >>>> > So, why not have a massive, general purpose interface so the type only can separate between containers --which would allow for cross-container polymorphism, i suppose, more easily, even though it's not necessarily the most widespread need. >>>> > So, do i miss something? Is there in fact a class of that kind? If so why not? >>>> > Thanks in advance! :) >>>> _______________________________________________ >>>> Beginners mailing list >>>> Beginners at haskell.org >>>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >>>> >>> >>> >>> >>> -- >>> Jeffrey Benjamin Brown >>> _______________________________________________ >>> Beginners mailing list >>> Beginners at haskell.org >>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >>> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From dennis.raddle at gmail.com Thu Jun 2 05:30:51 2016 From: dennis.raddle at gmail.com (Dennis Raddle) Date: Wed, 1 Jun 2016 22:30:51 -0700 Subject: [Haskell-beginners] Haskell and design patterns Message-ID: I have been using Haskell on and off, as a hobbyist, for five years. I haven't been diligent in training myself on it, so I am learning slowly. It was confusing at first, coming from an imperative background. It occurred to me the other day that Haskell typeclasses are a kind of "design pattern." They identify a common pattern and provide a solution. I've been reading about design patterns in C++ for years. Haskell patterns are a twist on that. The imperative view looks at a task in a certain way, often conceiving of it as steps that mimic how human thoughts would go, and finding big general patterns that occur in different big applications. I don't want to speak for all of Haskell, but at least some Haskell patterns are smaller-scale and more attuned to the language of programming rather than the language of human thought. For instance, the Monad. The common use case is this---you have some "things," and you have a "container" that can accept more than one type of "thing." The common patterns are - you need to wrap things in the container - you need to unwrap things - you need to modify things while in their container - you have functions that operate on containers - you have functions that operate on the things, but maybe you don't want to unwrap them first. or maybe you do. To an imperative programmer, this is bizarre. What things are you talking about? What containers? You have not defined either one, so why can you say anything specific? Why all this emphasis on wrapping and unwrapping? Yet this is a design pattern all the same. It gets weird when you realize that the Maybe monad, conceived in human-thought terms, has totally different behavior than the list monad. Yet they are the same design pattern and have a relationship that is more concisely expressed mathematically than in human thought. The abundance of operators for wrapping/unwrapping/operating seems, if I understand right, closely related to the conciseness of Haskell. If you can use your containers without unwrapping them first, then by all means you don't want extra syntax just to do so. Same if you have functions that only operate on unwrapped things. Haskell patterns are "lightweight" also helping with the conciseness. The closest thing to a "container" in C++ is a class, which is a dozen times heavier than a Functor, Applicative, or Monad. Actually you really need a "template class" which is like a tank compared to Functor which is a skinny guy fighting with a short knife (who can usually get the job done just fine, thank you). Any comments welcome. I'm just trying to get a good perspective on Haskell. Mike -------------- next part -------------- An HTML attachment was scrubbed... URL: From rpglover64 at gmail.com Thu Jun 2 16:01:53 2016 From: rpglover64 at gmail.com (Alex Rozenshteyn) Date: Thu, 02 Jun 2016 16:01:53 +0000 Subject: [Haskell-beginners] Haskell and design patterns In-Reply-To: References: Message-ID: Sounds reasonable. A few comments: Avoid the temptation to think of monads as "containers" as much as possible, some containers aren't monads (Set, for example) and many monads aren't containers (IO, Reader, Writer, State, etc.). As I understand "design pattern"s, they are approaches to solving problems that cannot be completely abstracted away. In that sense, "monad"s are no stranger a design pattern than "visitor". Some resources (many of which could be found by searching for "haskell design patterns", but which I personally found interesting): Design patterns for functional strategic programming (discusses patterns which are found in functional programming) http://blog.ezyang.com/2010/05/design-patterns-in-haskel/ (relates the original GoF patterns to Haskell alternatives) http://www.haskellforall.com/2012/08/the-category-design-pattern.html http://www.haskellforall.com/2012/09/the-functor-design-pattern.html (more design principles than design patterns, IMO, but good, clear reads) http://dev.stephendiehl.com/hask/ (an all around amazing resource of curated material) On Thu, Jun 2, 2016 at 1:30 AM Dennis Raddle wrote: > I have been using Haskell on and off, as a hobbyist, for five years. I > haven't been diligent in training myself on it, so I am learning slowly. It > was confusing at first, coming from an imperative background. > > It occurred to me the other day that Haskell typeclasses are a kind of > "design pattern." They identify a common pattern and provide a solution. > I've been reading about design patterns in C++ for years. Haskell patterns > are a twist on that. > > The imperative view looks at a task in a certain way, often conceiving of > it as steps that mimic how human thoughts would go, and finding big general > patterns that occur in different big applications. > > I don't want to speak for all of Haskell, but at least some Haskell > patterns are smaller-scale and more attuned to the language of programming > rather than the language of human thought. > > For instance, the Monad. The common use case is this---you have some > "things," and you have a "container" that can accept more than one type of > "thing." The common patterns are > > - you need to wrap things in the container > - you need to unwrap things > - you need to modify things while in their container > - you have functions that operate on containers > - you have functions that operate on the things, but maybe you don't want > to unwrap them first. or maybe you do. > > To an imperative programmer, this is bizarre. What things are you talking > about? What containers? You have not defined either one, so why can you say > anything specific? Why all this emphasis on wrapping and unwrapping? > > Yet this is a design pattern all the same. It gets weird when you realize > that the Maybe monad, conceived in human-thought terms, has totally > different behavior than the list monad. Yet they are the same design > pattern and have a relationship that is more concisely expressed > mathematically than in human thought. > > The abundance of operators for wrapping/unwrapping/operating seems, if I > understand right, closely related to the conciseness of Haskell. If you can > use your containers without unwrapping them first, then by all means you > don't want extra syntax just to do so. Same if you have functions that only > operate on unwrapped things. > > Haskell patterns are "lightweight" also helping with the conciseness. The > closest thing to a "container" in C++ is a class, which is a dozen times > heavier than a Functor, Applicative, or Monad. Actually you really need a > "template class" which is like a tank compared to Functor which is a skinny > guy fighting with a short knife (who can usually get the job done just > fine, thank you). > > Any comments welcome. I'm just trying to get a good perspective on Haskell. > > Mike > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From peterjoel at gmail.com Fri Jun 3 10:40:06 2016 From: peterjoel at gmail.com (Peter Hall) Date: Fri, 3 Jun 2016 11:40:06 +0100 Subject: [Haskell-beginners] why is there no typeclass common to all containers? In-Reply-To: References: Message-ID: > As for why Haskell doesn't allow natural overloading of any function name merely by choosing another name, does anyone know? Haskell requires that overloaded functions are part of a typeclass. This isn't a big requirement - you can easily make any type into an instance of a new typeclass. The reason why this is important is that it ensures that the meaning and intent of the function are the same, not just a coincidental naming collision. Peter On 1 June 2016 at 18:18, Silent Leaf wrote: > map and set are not what? I didn't get it. > > That's cool, I'll look into it! > As for why Haskell doesn't allow natural overloading of any function name > merely by choosing another name, does anyone know? > > > Le mercredi 1 juin 2016, Alex Rozenshteyn a ?crit : > > Map is (you map over the values, not the keys). > > > > On Wed, Jun 1, 2016 at 1:14 AM Tony Morris wrote: > >> > >> Map and Set are not. > >> > >> On 01/06/2016 8:57 AM, "Jeffrey Brown" wrote: > >>> > >>> In Haskell typeclasses are based on what you want to do with > something. If, for instance, you want to be able to map over a container, > you can make it an instance of class Functor -- which all the standard > containers (List, Map, Set, Tree, Maybe ...) already are. > >>> On Tue, May 31, 2016 at 3:26 PM, Silent Leaf > wrote: > >>>> > >>>> In fact it all comes down to trying to add partially a feature absent > from the Haskell language, which is the ability to distinguish values both > on name *and* on type --thus allowing two variables of the same name if > they have different types. > >>>> Honestly i don't see the drawback of that name system, but i guess > there must be one otherwise it'd have been chosen by default instead of the > typeblind current name system. > >>>> > >>>> Le mercredi 1 juin 2016, Silent Leaf a > ?crit : > >>>> > All in the title. I haven't used them much, but I saw Map or Vector > types were forcing the user to use qualified functions unless you want > nameclash with the more basic, typically list-oriented functions. > >>>> > So, why not have a massive, general purpose interface so the type > only can separate between containers --which would allow for > cross-container polymorphism, i suppose, more easily, even though it's not > necessarily the most widespread need. > >>>> > So, do i miss something? Is there in fact a class of that kind? If > so why not? > >>>> > Thanks in advance! :) > >>>> _______________________________________________ > >>>> Beginners mailing list > >>>> Beginners at haskell.org > >>>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > >>>> > >>> > >>> > >>> > >>> -- > >>> Jeffrey Benjamin Brown > >>> _______________________________________________ > >>> Beginners mailing list > >>> Beginners at haskell.org > >>> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > >>> > >> _______________________________________________ > >> Beginners mailing list > >> Beginners at haskell.org > >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > > > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From silent.leaf0 at gmail.com Fri Jun 3 16:44:50 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Fri, 3 Jun 2016 18:44:50 +0200 Subject: [Haskell-beginners] "type" declarations: utterly transparent synonyms? Message-ID: I'd like to be sure when one defines a type with "type", it truly merely creates a synonym, and no matter what one could replace the left side by the right side in the whole program, and vice versa, and it wouldn't change a thing in the actual meaning, value of the program. Eg if i define: type In2 t = t -> t -> t I can thereafter replace for any type t, any signature like f :: t -> t -> t with f :: In2 t then strictly no consequence other than visual in the source code, by me, will occur. Thanks! -------------- next part -------------- An HTML attachment was scrubbed... URL: From imantc at gmail.com Fri Jun 3 16:54:17 2016 From: imantc at gmail.com (Imants Cekusins) Date: Fri, 3 Jun 2016 18:54:17 +0200 Subject: [Haskell-beginners] "type" declarations: utterly transparent synonyms? In-Reply-To: References: Message-ID: it seems so.. different synonyms with similar "content" are substituted / matched without errors: data D = S String | I Int deriving (Eq,Ord) type A = D type B = D compiler "won't mind" if Set A is replaced with Set B ? -------------- next part -------------- An HTML attachment was scrubbed... URL: From bergey at alum.mit.edu Fri Jun 3 18:01:00 2016 From: bergey at alum.mit.edu (Daniel Bergey) Date: Fri, 03 Jun 2016 14:01:00 -0400 Subject: [Haskell-beginners] "type" declarations: utterly transparent synonyms? In-Reply-To: References: Message-ID: <87poryw3s3.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> Yes, it is as you say. The Haddock documentation will use the type synonym if (and only if) you use it in the type of f. Call sites of f, and the result of f, are the same regardless. For example, this is fine: f :: t -> t -> t g :: Int2 t g = f cheers, bergey On 2016-06-03 at 12:44, Silent Leaf wrote: > I'd like to be sure when one defines a type with "type", it truly merely creates a > synonym, and no matter what one could replace the left side by the right side in the > whole program, and vice versa, and it wouldn't change a thing in the actual meaning, > value of the program. > > Eg if i define: > type In2 t = t -> t -> t > I can thereafter replace for any type t, any signature like > f :: t -> t -> t > with > f :: In2 t > then strictly no consequence other than visual in the source code, by me, will occur. > Thanks! > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners From silent.leaf0 at gmail.com Fri Jun 3 22:28:46 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Sat, 4 Jun 2016 00:28:46 +0200 Subject: [Haskell-beginners] "type" declarations: utterly transparent synonyms? In-Reply-To: <87poryw3s3.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> References: <87poryw3s3.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> Message-ID: Thanks! Le vendredi 3 juin 2016, Daniel Bergey a ?crit : > Yes, it is as you say. The Haddock documentation will use the type > synonym if (and only if) you use it in the type of f. Call sites of f, > and the result of f, are the same regardless. > > For example, this is fine: > > f :: t -> t -> t > > g :: Int2 t > g = f > > cheers, > bergey > > On 2016-06-03 at 12:44, Silent Leaf wrote: >> I'd like to be sure when one defines a type with "type", it truly merely creates a >> synonym, and no matter what one could replace the left side by the right side in the >> whole program, and vice versa, and it wouldn't change a thing in the actual meaning, >> value of the program. >> >> Eg if i define: >> type In2 t = t -> t -> t >> I can thereafter replace for any type t, any signature like >> f :: t -> t -> t >> with >> f :: In2 t >> then strictly no consequence other than visual in the source code, by me, will occur. >> Thanks! >> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From silent.leaf0 at gmail.com Fri Jun 3 23:28:37 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Sat, 4 Jun 2016 01:28:37 +0200 Subject: [Haskell-beginners] help on writing a typeclass Message-ID: I got a function, named mdk (don't ask). It happens it's a method of a class, as follows: class C a where mdk :: C b => a -> b -> (a, b) yet i got another function, called so far mdk' mdk' :: C b => b -> a -> (a, b) Say there are the following instances: instance C X where mdk x b = ... :: C b => (X, b) mdk' b x = ... :: C b => (X, b) instance C Y where mdk y b = ... :: C b => (Y, b) mdk' b y = ... :: C b => (Y, b) if you get what's happening, mdk and mdk' are basically the same method, save for the final type-result, which is reversed, without data loss mind you (aka (A, B) and (B, A) could be the same type, if only i knew of a way to make a type in haskell without forcing the order (a kind of set or something). so, there are four cases: input have types, in this order, X and Y, and expected output is (X, Y): then mdk from X's instance of C is called/must be used; input have types Y and X, output (X, Y): X's mdk' input X and Y, output (Y, X): Y's mdk input Y and X, output (Y, X): Y's mdk' it might seem confusing, but all amounts to the issue that even though (Y, X) is strictly equivalent, in my program, to (X, Y), in principle haskell differentiate the types. thus i have to write two versions of mdk for each type, even though the methods "X's mdk" and "Y's mdk'" are identical, and same for the two other methods. indeed: mdk :: C b => X -> b -> (X, b) mdk' :: C b => b -> Y -> (Y, b) are identical signatures, if in the first one you replace `b` with Y, and in the latter you replace `b` with X, and ofc if you consider (X,Y) == (Y,X). only one of those two methods should be enough to handle the job, and be chosen by the compiler on the sole value of the type of the first variable; but the fact both methods return tuples of "mirrored" types, crushes that. if i only write `mdk` instances, as soon as the compiler will meet this following signature: mdk :: a -> b -> (b, a) it will crash an exception, because mdk's original signature has for output value a tuple whose first type should here be `a`, because it's meant to be the type of the first argument, not the second. thus, at last my question: can i tell the compiler to consider (b, a) and (a, b) as identical types (don't worry it's not really a tuple in my program, but it's equivalent)? if not, can i make an overloading of mdk so it accepts both a->b->(a,b) and a->b->(b,a)? hope i didn't lose anyone. if so, do tell me, i'll try to clarify. thanks in advance of the time spent trying to understand my problem! -------------- next part -------------- An HTML attachment was scrubbed... URL: From silent.leaf0 at gmail.com Fri Jun 3 23:57:54 2016 From: silent.leaf0 at gmail.com (Silent Leaf) Date: Sat, 4 Jun 2016 01:57:54 +0200 Subject: [Haskell-beginners] help on writing a typeclass In-Reply-To: References: Message-ID: Got an idea, is it the right path? Are there bad consequences in using the extensions that are necessaries to make the code work? class Mdk binary a | binary -> a where mdk :: a -> b -> binary instance Mdk (a,b) a where mdk = ... :: a -> b -> (a,b) instance Mdk (b, a) a where mdk = ... :: a -> b -> (b, a) then, however, even if it works, mdk will never be part of the other class i was working on, and at that point i'm a bit lost on the consequences of this... Le samedi 4 juin 2016, Silent Leaf a ?crit : > I got a function, named mdk (don't ask). It happens it's a method of a class, as follows: > > class C a where > mdk :: C b => a -> b -> (a, b) > > yet i got another function, called so far mdk' > mdk' :: C b => b -> a -> (a, b) > > > Say there are the following instances: > instance C X where > mdk x b = ... :: C b => (X, b) > mdk' b x = ... :: C b => (X, b) > instance C Y where > mdk y b = ... :: C b => (Y, b) > mdk' b y = ... :: C b => (Y, b) > > if you get what's happening, mdk and mdk' are basically the same method, save for the final type-result, which is reversed, without data loss mind you (aka (A, B) and (B, A) could be the same type, if only i knew of a way to make a type in haskell without forcing the order (a kind of set or something). > so, there are four cases: > input have types, in this order, X and Y, and expected output is (X, Y): then mdk from X's instance of C is called/must be used; > input have types Y and X, output (X, Y): X's mdk' > input X and Y, output (Y, X): Y's mdk > input Y and X, output (Y, X): Y's mdk' > > it might seem confusing, but all amounts to the issue that even though (Y, X) is strictly equivalent, in my program, to (X, Y), in principle haskell differentiate the types. > thus i have to write two versions of mdk for each type, even though the methods "X's mdk" and "Y's mdk'" are identical, and same for the two other methods. > indeed: > mdk :: C b => X -> b -> (X, b) > mdk' :: C b => b -> Y -> (Y, b) > are identical signatures, if in the first one you replace `b` with Y, and in the latter you replace `b` with X, and ofc if you consider (X,Y) == (Y,X). > > only one of those two methods should be enough to handle the job, and be chosen by the compiler on the sole value of the type of the first variable; but the fact both methods return tuples of "mirrored" types, crushes that. if i only write `mdk` instances, as soon as the compiler will meet this following signature: > mdk :: a -> b -> (b, a) > it will crash an exception, because mdk's original signature has for output value a tuple whose first type should here be `a`, because it's meant to be the type of the first argument, not the second. > > thus, at last my question: can i tell the compiler to consider (b, a) and (a, b) as identical types (don't worry it's not really a tuple in my program, but it's equivalent)? > if not, can i make an overloading of mdk so it accepts both a->b->(a,b) and a->b->(b,a)? > > hope i didn't lose anyone. if so, do tell me, i'll try to clarify. > > thanks in advance of the time spent trying to understand my problem! -------------- next part -------------- An HTML attachment was scrubbed... URL: From rajasharan at gmail.com Sat Jun 4 04:40:59 2016 From: rajasharan at gmail.com (Raja) Date: Sat, 4 Jun 2016 00:40:59 -0400 Subject: [Haskell-beginners] Functions as containers; implications on being a Monad ((->) r) Message-ID: Everyone agrees ((->) r) is a Functor, an Applicative and a Monad but I've never seen any good writeup going into details of explaining this. So I was trying to brainstorm with my brother and went pretty far into the concept for quite a few hours, but still got stuck when it came to Monads. Before I showcase the question/problem I wanted to share our thinking process. Lets stick with common types like Maybe a, [a], simple function (a -> b) **Everything is a Container** Just 4 => this is a container wrapping some value [1,2,3] => this is a container wrapping bunch of values (+3) => this is a container wrapping domains & ranges (infinite dictionary) **When is a Container a Functor** If we can peek inside a container and apply a simple function (a->b) to each of its values and wrap the result back inside the container, then it becomes a Functor. Let's use (\x -> x+7) as simple function along with above three Containers (\x -> x+7) <$> Just 4 => Just 11 (\x -> x+7) <$> [1,2,3] => [8,9,10] (\x -> x+7) <$> (+3) => (+10) -- well there is no Show defined but you get the idea **When is a Container an Applicative** The simple function from above is also now wrapped inside a container and we should be able to peek to use it just like functor. Also lets simplify (\x -> x+7) to (+7). Just (+7) <*> Just 4 => Just 11 [(+7)] <*> [1,2,3] => [8,9,10] (\x -> (+7)) <*> (+3) => (+10) -- again no Show defined but works when pass a number -- but (+7) still needs to be wrapped in a Container though **When is a Container a Monad** This time we don't have a simple function (a->b) instead we have a non-simple function (a -> Container). But rest stays almost the same. We have to first peek inside a container and apply non-simple function to each of its values. Since its a non-simple function we need to collect all the returned Containers, unwrap them and wrap them all back in a Container again. (it almost feels like unwrap and wrapping them back is going to complicate things) Also Non-simple function cannot be reused as is for all three Containers like in Functors & Applicatives. Just 4 >>= (\x -> Just (x+7)) => Just 11 [1,2,3] >>= (\x -> [x+7]) => [8,9,10] (+3) >>= (\x -> (+7)) => (+7) Wait a minute ... the last line doesn't look right. Or should I say it doesn't feel right to discard the `x' altogether. OK let's jump to do this: (+3) >>= (\x -> (+x)) => ??? -- apparently this solves for the equation: f(x) = 2x + 3 (is 2x + 3 obvious for anyone??? it took us way longer to derive it) (Does it have anything to do with Monad laws by any chance?) This is where it feels like "Functions as containers" concept starts to breakdown; its not the right analogy for Monads. What does it even mean to unwrap a bunch of functions and wrap them back again? Hope this intrigues some of you as it did to us. Any thoughts and comments greatly appreciated. Thanks, Raja -------------- next part -------------- An HTML attachment was scrubbed... URL: From imantc at gmail.com Sat Jun 4 07:29:03 2016 From: imantc at gmail.com (Imants Cekusins) Date: Sat, 4 Jun 2016 09:29:03 +0200 Subject: [Haskell-beginners] help on writing a typeclass In-Reply-To: References: Message-ID: would this work: {-# LANGUAGE MultiParamTypeClasses, InstanceSigs #-} module Mdk where data C a b = Ab a b | Ba b a class Mdk a b where mdk::a -> b -> C a b instance (Eq a, Eq b) => Eq (C a b) where (==)::C a b -> C a b -> Bool (==) (Ab a1 b1) (Ab a2 b2) = a1 == a2 && b1 == b2 (==) (Ab a1 b1) (Ba b2 a2) = a1 == a2 && b1 == b2 (==) (Ba b2 a2) (Ab a1 b1) = a1 == a2 && b1 == b2 (==) (Ba b2 a2) (Ba b1 a1) = a1 == a2 && b1 == b2 ?? -------------- next part -------------- An HTML attachment was scrubbed... URL: From i.caught.air at gmail.com Sat Jun 4 14:27:05 2016 From: i.caught.air at gmail.com (Alex Belanger) Date: Sat, 4 Jun 2016 10:27:05 -0400 Subject: [Haskell-beginners] Functions as containers; implications on being a Monad ((->) r) In-Reply-To: References: Message-ID: Does it help if I bring your: (\x -> x+7) <$> (+3) => (+10) It doesn't magically become `(+10)`. The previous step unseen is `(+7) . (+3)`. fmap for ((->) r) is defined as function composition `.`. fmap f g = f . g You can think of functors as containers or contexts; both analogies work well up to some degree (with the latter maybe more abstract and thus flexible). Another small terminology tip that could help you with your thinkering might be to call ((->) r) a partially applied function. Suddently, it narrows how you can potentially use/combine them. Last tip, Monad ((->) r) is commonly refered to as the Reader monad. Example of how it'd be used: doThings = do a <- (*2) b <- (+10) return (a + b) Notice how we can work with partially applied functions to which something have yet to be applied and create a new partial function whose argument is going to fill all the open holes. This isn't easy to explain without looking at the types of everything, so I encourage you to write it down and work out the types (: Alex On Jun 4, 2016 12:41 AM, "Raja" wrote: Everyone agrees ((->) r) is a Functor, an Applicative and a Monad but I've never seen any good writeup going into details of explaining this. So I was trying to brainstorm with my brother and went pretty far into the concept for quite a few hours, but still got stuck when it came to Monads. Before I showcase the question/problem I wanted to share our thinking process. Lets stick with common types like Maybe a, [a], simple function (a -> b) **Everything is a Container** Just 4 => this is a container wrapping some value [1,2,3] => this is a container wrapping bunch of values (+3) => this is a container wrapping domains & ranges (infinite dictionary) **When is a Container a Functor** If we can peek inside a container and apply a simple function (a->b) to each of its values and wrap the result back inside the container, then it becomes a Functor. Let's use (\x -> x+7) as simple function along with above three Containers (\x -> x+7) <$> Just 4 => Just 11 (\x -> x+7) <$> [1,2,3] => [8,9,10] (\x -> x+7) <$> (+3) => (+10) -- well there is no Show defined but you get the idea **When is a Container an Applicative** The simple function from above is also now wrapped inside a container and we should be able to peek to use it just like functor. Also lets simplify (\x -> x+7) to (+7). Just (+7) <*> Just 4 => Just 11 [(+7)] <*> [1,2,3] => [8,9,10] (\x -> (+7)) <*> (+3) => (+10) -- again no Show defined but works when pass a number -- but (+7) still needs to be wrapped in a Container though **When is a Container a Monad** This time we don't have a simple function (a->b) instead we have a non-simple function (a -> Container). But rest stays almost the same. We have to first peek inside a container and apply non-simple function to each of its values. Since its a non-simple function we need to collect all the returned Containers, unwrap them and wrap them all back in a Container again. (it almost feels like unwrap and wrapping them back is going to complicate things) Also Non-simple function cannot be reused as is for all three Containers like in Functors & Applicatives. Just 4 >>= (\x -> Just (x+7)) => Just 11 [1,2,3] >>= (\x -> [x+7]) => [8,9,10] (+3) >>= (\x -> (+7)) => (+7) Wait a minute ... the last line doesn't look right. Or should I say it doesn't feel right to discard the `x' altogether. OK let's jump to do this: (+3) >>= (\x -> (+x)) => ??? -- apparently this solves for the equation: f(x) = 2x + 3 (is 2x + 3 obvious for anyone??? it took us way longer to derive it) (Does it have anything to do with Monad laws by any chance?) This is where it feels like "Functions as containers" concept starts to breakdown; its not the right analogy for Monads. What does it even mean to unwrap a bunch of functions and wrap them back again? Hope this intrigues some of you as it did to us. Any thoughts and comments greatly appreciated. Thanks, Raja _______________________________________________ Beginners mailing list Beginners at haskell.org http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners -------------- next part -------------- An HTML attachment was scrubbed... URL: From bergey at alum.mit.edu Sat Jun 4 16:56:02 2016 From: bergey at alum.mit.edu (Daniel Bergey) Date: Sat, 04 Jun 2016 12:56:02 -0400 Subject: [Haskell-beginners] Functions as containers; implications on being a Monad ((->) r) In-Reply-To: References: Message-ID: <87k2i4x599.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> I think "a functor is a container" is not so helpful. It works OK for Maybe and List, but it doesn't seem helpful in understanding Either, Reader, Writer, State, Continuation, promises. For the instance ((->) r), it's important to keep track of which argument is the r. I think it helps to write the lambdas explicitly, rather than the point-free (+3). Keeping the type variables straight is also a reminder that all these need to work for any types r, a, b, not only when all three types are Int: (r ~ a ~ b ~ Int). So we have: fmap :: (a -> b) -> (r -> a) -> (r -> b) fmap f g = \r -> f (g r) fmap (\x -> x + 7) (\r -> r + 3) = \r -> (r + 3) + 7 (<*>) :: (r -> a -> b) -> (r -> a) -> (r -> b) f <*> g = \r -> f r (g r) Since r, a, b may all be different types, this is the only possible definition. (\r -> (\x -> x + 7)) <*> (\r -> r + 3) = \r -> (r + 3) + 7 Note that the function on the left of <*> ignores its r parameter, so this is exactly the same as the fmap example. This follows the law (for any Applicative) that fmap f === pure f <*> For an example that doesn't ignore the r: (\r -> (\x -> r + x)) <*> (\r -> r + 3) = \r -> r + (r + 3) Note also that the function on the left takes the argument of type r first, and the argument of type a second. The second argument to >>=, on the other hand, takes an a, then an r: (>>=) :: (r -> a) -> (a -> (r -> b)) -> (r -> b) f >>= g = \r -> g (f r) (\r -> r + 3) >>= (\x -> (\r -> r + 7)) = \r -> r + 7 Here the function on the right of >>= ignores its argument, so this isn't very interesting. (\r -> r + 3) >>= (\x -> (\r -> r + x)) = \r -> r + (r + 3) is a bit more interesting. It uses both functions, but it's exactly the same as the second Applicative example. I *think* it's the case that for (r ->), there isn't anything we can do with the Monad instance that we can't do with Applicative. If someone can confirm or refute that, I'd appreciate it. That's of course not true in general for other monads. Hope this helps. bergey On 2016-06-04 at 00:40, Raja wrote: > Everyone agrees ((->) r) is a Functor, an Applicative and a Monad but I've never seen > any good writeup going into details of explaining this. > > So I was trying to brainstorm with my brother and went pretty far into the concept for > quite a few hours, but still got stuck when it came to Monads. > > Before I showcase the question/problem I wanted to share our thinking process. > > Lets stick with common types like Maybe a, [a], simple function (a -> b) > > **Everything is a Container** > > ?Just 4 => this is a container wrapping some value > [1,2,3] => this is a container wrapping bunch of values > (+3) => this is a container wrapping domains & ranges (infinite dictionary) > > **When is a Container a Functor** > > If we can peek inside a container and apply a simple function (a->b) to each of its > values and wrap the result back inside the container, then it becomes a Functor. > > Let's use (\x -> x+7) as simple function along with above three Containers > > (\x -> x+7) <$> Just 4 => Just 11 > (\x -> x+7) <$> [1,2,3] => [8,9,10] > (\x -> x+7) <$> (+3) => (+10) ?-- well there is no Show defined but you get the idea > > **When is a Container an Applicative** > > The simple function from above is also now wrapped inside a container and we should be > able to peek to use it just like functor. Also lets simplify (\x -> x+7) to (+7). > > Just (+7) <*> Just 4 => Just 11 > [(+7)] <*> [1,2,3] => [8,9,10] > (\x -> (+7)) <*> (+3) => (+10) -- again no Show defined but works when pass a number > -- but (+7) still needs to be wrapped in a Container though > > **When is a Container a Monad** > > This time we don't have a simple function (a->b) instead we have a non-simple function > (a -> Container). But rest stays almost the same.? > > We have to first peek inside a container and apply non-simple function to each of its > values. Since its a non-simple function we need to collect all the returned Containers, > unwrap them and wrap them all back in a Container again.? > (it almost feels like unwrap and wrapping them back is going to complicate things) > > Also Non-simple function cannot be reused as is for all three Containers like in > Functors & Applicatives. > > Just 4 >>= (\x -> Just (x+7)) => Just 11 > [1,2,3] >>= (\x -> [x+7]) => [8,9,10] > (+3) >>= (\x -> (+7)) => (+7)? > > Wait a minute ... the last line doesn't look right. Or should I say it doesn't feel > right to discard the `x' altogether.? > > OK let's jump to do this: > (+3) >>= (\x -> (+x)) => ??? -- apparently this solves for the equation: f(x) = 2x + 3 > > (is 2x + 3 obvious for anyone??? it took us way longer to derive it) > (Does it have anything to do with Monad laws by any chance?) > > This is where it feels like "Functions as containers" concept starts to breakdown; its > not the right analogy for Monads.? > > What does it even mean to unwrap a bunch of functions and wrap them back again? > > Hope this intrigues some of you as it did to us. Any thoughts and comments greatly > appreciated. > > Thanks, > Raja > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners From gesh at gesh.uni.cx Sun Jun 5 00:10:47 2016 From: gesh at gesh.uni.cx (Gesh) Date: Sun, 5 Jun 2016 03:10:47 +0300 Subject: [Haskell-beginners] Functions as containers; implications on being a Monad ((->) r) In-Reply-To: <87k2i4x599.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> References: <87k2i4x599.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> Message-ID: On 2016-06-04 19:56, Daniel Bergey wrote: > I think "a functor is a container" is not so helpful. It works OK for > Maybe and List, but it doesn't seem helpful in understanding Either, > Reader, Writer, State, Continuation, promises. This is correct. However, a large class of types form what are called "Representable Functors". These include Lists, Trees, ((->) r), etc. A representable functor is any type f with an isomorphism `(f a ~ r -> a)` for some r. For example, `Stream a ~ Natural -> a` under the isomorphism: > toFunction xs = \i -> xs !! i > toList f = fromList $ map f [0..] > I *think* it's the case that for (r ->), there isn't anything we can do > with the Monad instance that we can't do with Applicative. If someone > can confirm or refute that, I'd appreciate it. That's of course not > true in general for other monads. Indeed, for any representable functor, this all follows from the fact that we can write a lawful join from Reader's <*>. Letting `join m = flip ($) <*> m`, we have: > (join . pure) x = \r -> ($ r) (const x r) = \r -> x $ r = x > (join . fmap pure) x = \r -> ($ r) ((pure . x) r) = \r -> (const (x r)) r = \r -> x r = x > (join . fmap join) x = \r -> ($ r) ((join . x) r) = \r -> join (x r) r = \r -> (\s -> ($s) (x r s)) r > = \r -> x r r r = \r -> ($r) (\s -> x s s) r = join (\s -> ($s) (x s)) = (join . join) x Hence, given the applicative instance for Reader, we obtain the Monad instance for free. Therefore, working under the isomorphism, we have the same for any representable functor. In particular, this gives that Stream is a Monad, where return gives the constant stream and join takes the diagonal of a stream of streams. Again, as noted, this is more or less the only way in which the "Functors/Applicatives/Monads are nice/nicer/nicest containers" analogy works. There are more things in heaven and earth than are described in that analogy, but it's a start. Hope this helps, and that it lacks errors/misleading material, Gesh P.S. Code for working with representable functors can be found in representable-functors. Code for working with Streams can be found in streams. Both are on Hackage. From kolsrud at gmail.com Thu Jun 9 11:28:49 2016 From: kolsrud at gmail.com (=?UTF-8?Q?=C3=98ystein_Kolsrud?=) Date: Thu, 9 Jun 2016 13:28:49 +0200 Subject: [Haskell-beginners] Haskell and design patterns In-Reply-To: References: Message-ID: I would argue that the closes thing you get to type classes in OO languages are interfaces. The concept of an interface is also a pattern though, but it's so tightly integrated in most OO languages these days that you hardly think of it as a pattern anymore (just like you rarely think if inheritance as a pattern). An interface in the OO world is usually a set of function that any type who implements the interface is expected to provide. Same thing with type classes in Haskell. As for the monad pattern feeling strange for imperative (and OO programmers), the pattern is actually used quite a lot even in the OO domain, but one rarely talks if it using that name. A very clear example of this is the Task class used for asynchronous operations in C#. It has both the bind operation (Task.ContinueWith) and return (Task.FromResult) and captures the sequential nature of operations that is exactly what the monad type class is used for in Haskell. On Thu, Jun 2, 2016 at 7:30 AM, Dennis Raddle wrote: > I have been using Haskell on and off, as a hobbyist, for five years. I > haven't been diligent in training myself on it, so I am learning slowly. It > was confusing at first, coming from an imperative background. > > It occurred to me the other day that Haskell typeclasses are a kind of > "design pattern." They identify a common pattern and provide a solution. > I've been reading about design patterns in C++ for years. Haskell patterns > are a twist on that. > > The imperative view looks at a task in a certain way, often conceiving of > it as steps that mimic how human thoughts would go, and finding big general > patterns that occur in different big applications. > > I don't want to speak for all of Haskell, but at least some Haskell > patterns are smaller-scale and more attuned to the language of programming > rather than the language of human thought. > > For instance, the Monad. The common use case is this---you have some > "things," and you have a "container" that can accept more than one type of > "thing." The common patterns are > > - you need to wrap things in the container > - you need to unwrap things > - you need to modify things while in their container > - you have functions that operate on containers > - you have functions that operate on the things, but maybe you don't want > to unwrap them first. or maybe you do. > > To an imperative programmer, this is bizarre. What things are you talking > about? What containers? You have not defined either one, so why can you say > anything specific? Why all this emphasis on wrapping and unwrapping? > > Yet this is a design pattern all the same. It gets weird when you realize > that the Maybe monad, conceived in human-thought terms, has totally > different behavior than the list monad. Yet they are the same design > pattern and have a relationship that is more concisely expressed > mathematically than in human thought. > > The abundance of operators for wrapping/unwrapping/operating seems, if I > understand right, closely related to the conciseness of Haskell. If you can > use your containers without unwrapping them first, then by all means you > don't want extra syntax just to do so. Same if you have functions that only > operate on unwrapped things. > > Haskell patterns are "lightweight" also helping with the conciseness. The > closest thing to a "container" in C++ is a class, which is a dozen times > heavier than a Functor, Applicative, or Monad. Actually you really need a > "template class" which is like a tank compared to Functor which is a skinny > guy fighting with a short knife (who can usually get the job done just > fine, thank you). > > Any comments welcome. I'm just trying to get a good perspective on Haskell. > > Mike > > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > > -- Mvh ?ystein Kolsrud -------------- next part -------------- An HTML attachment was scrubbed... URL: From martin.drautzburg at web.de Sun Jun 12 13:38:02 2016 From: martin.drautzburg at web.de (martin) Date: Sun, 12 Jun 2016 15:38:02 +0200 Subject: [Haskell-beginners] How to hunt this space-leak Message-ID: <575D65BA.6030707@web.de> Hello all, I hope I am not asking for too much, as to explain my problem, you need to read my code, which may not be a pleasure. I am trying to write a "Logger", which formats and accumulates log-entries in a monoid. From there I went to writing an "accumulating" logger, i.e. one which can accumulate (sum/avg) over entries made with a certain timespan. My problen is memory consumption. In the test below I stress the logger with 1 million values, but in the end result, there are only 10 entries left, because it accumulates over 100,000. Memory goes up to apx 100MB. When I comment out the line, which logs the accumulated value (see -- > below), memory stays below 10MB. I dont understand why this is so. After all, the difference is only whether or not those 10 entries are logged or not. Can someone explain this? {-# LANGUAGE BangPatterns#-} import Data.Monoid import Control.Monad.State.Strict import System.TimeIt import Text.Show.Pretty import Debug.Trace ------------------------------------------------------------ -- Simple Time Stuff ------------------------------------------------------------ type Instant = Double type Interval = Double type Timed a = (Instant, a) instant = fst ------------------------------------------------------------ -- Logger based on State monad ------------------------------------------------------------ data SLogger a l = SLgr {runSLogger :: a ->State l (SLogger a l)} type SLogFormatter a l = a -> l accLogger :: (Monoid c, Show a) => (Instant, Interval, [Timed b]) -> SLogFormatter (Timed a) [Timed b] -> SLogFormatter [Timed b] [Timed c] -> SLogger (Timed a) [Timed c] accLogger (tx, dt, tas) fmt1 fmt2 = SLgr $ \(!ta) -> let x = fmt1 ta !tas' = x <> tas in if instant ta < tx then do -- keep accumulating return $ accLogger (tx, dt, tas') fmt1 fmt2 else do -- compute new log and reset accumulator !l0 <- get -- > put $ fmt2 tas' <> l0 return $ accLogger ((tx+dt), dt, []) fmt1 fmt2 accFmt1 ta = [ta] accFmt2 tas = [(fst $ head tas, "hello from accFormatter")] -- apply logger to a list of as stest lgr [] = return lgr stest lgr (a:as) = do lgr' <- (runSLogger lgr) a stest lgr' as main2 = do let as = zip [1.0 .. 1000000.0] [1..1000000] :: [(Instant, Int)] log = execState (stest (accLogger (100000.0,100000.0,[]) accFmt1 accFmt2 ) as) [(0,"init")] timeIt $ putStrLn $ ppShow log putStrLn "done" main = main2 From martin.drautzburg at web.de Sun Jun 12 21:11:05 2016 From: martin.drautzburg at web.de (martin) Date: Sun, 12 Jun 2016 23:11:05 +0200 Subject: [Haskell-beginners] State Monad in constant space? Message-ID: <575DCFE9.7070904@web.de> Hello all, the State Monad wraps around a computation s -> (s,a). Inside a do block I am actually assembling such a computation. Now when I do this many times, i.e. in a recursice call, I am builing a huge expression m a >>= (\a -> mb) >>= (\b -> mc) ... The result of this expression is a function s -> (s,a). But I cannot see how the space for this expression can be reclaimed, and how it could ever run in constant space. Once I call runState and I provide an initial s, I have some hope, but before? How is this supposed to work? How do I avoid allocating space for this huge expression? From haskell at erebe.eu Mon Jun 13 11:13:39 2016 From: haskell at erebe.eu (=?UTF-8?Q?Romain_G=C3=A9rard?=) Date: Mon, 13 Jun 2016 13:13:39 +0200 Subject: [Haskell-beginners] How to hunt this space-leak In-Reply-To: <575D65BA.6030707@web.de> References: <575D65BA.6030707@web.de> Message-ID: <00c0c074424926dde09858a61f163d06@erebe.eu> Hello, I have used the technique described below[1] with great success. To be fair, debugging space leak in haskell is kinda hard, even knowing that you have one is a big step forward. Maybe it is possible to create a program like valgrind for haskell, but I lack the knowledge to tell if it's possible or not. [1] http://neilmitchell.blogspot.fr/2015/09/detecting-space-leaks.html Regards Le 2016-06-12 15:38, martin a ?crit?: > Hello all, > > I hope I am not asking for too much, as to explain my problem, you > need to read my code, which may not be a pleasure. > > I am trying to write a "Logger", which formats and accumulates > log-entries in a monoid. From there I went to writing an > "accumulating" logger, i.e. one which can accumulate (sum/avg) over > entries made with a certain timespan. > > My problen is memory consumption. In the test below I stress the > logger with 1 million values, but in the end result, > there are only 10 entries left, because it accumulates over 100,000. > Memory goes up to apx 100MB. > > When I comment out the line, which logs the accumulated value (see -- > > below), memory stays below 10MB. I dont > understand why this is so. After all, the difference is only whether > or not those 10 entries are logged or not. > > Can someone explain this? > > > > {-# LANGUAGE BangPatterns#-} > > > import Data.Monoid > import Control.Monad.State.Strict > import System.TimeIt > import Text.Show.Pretty > import Debug.Trace > > > ------------------------------------------------------------ > -- Simple Time Stuff > ------------------------------------------------------------ > type Instant = Double > type Interval = Double > type Timed a = (Instant, a) > instant = fst > > ------------------------------------------------------------ > -- Logger based on State monad > ------------------------------------------------------------ > > data SLogger a l = SLgr {runSLogger :: a ->State l (SLogger a l)} > type SLogFormatter a l = a -> l > > > accLogger :: (Monoid c, Show a) => > (Instant, Interval, [Timed b]) -> > SLogFormatter (Timed a) [Timed b] -> SLogFormatter [Timed > b] [Timed c] -> SLogger (Timed a) [Timed c] > > > accLogger (tx, dt, tas) fmt1 fmt2 = SLgr $ \(!ta) -> > let x = fmt1 ta > !tas' = x <> tas > in > if instant ta < tx > then do > -- keep accumulating > return $ accLogger (tx, > dt, tas') fmt1 fmt2 > else do > -- compute new log and > reset accumulator > !l0 <- get > -- > put $ fmt2 tas' <> l0 > return $ accLogger > ((tx+dt), dt, []) fmt1 fmt2 > > > > accFmt1 ta = [ta] > accFmt2 tas = [(fst $ head tas, "hello from accFormatter")] > > -- apply logger to a list of as > stest lgr [] = return lgr > stest lgr (a:as) = do > lgr' <- (runSLogger lgr) a > stest lgr' as > > > main2 = do > let as = zip [1.0 .. 1000000.0] [1..1000000] :: [(Instant, Int)] > log = execState (stest (accLogger (100000.0,100000.0,[]) > accFmt1 accFmt2 ) as) [(0,"init")] > timeIt $ putStrLn $ ppShow log > putStrLn "done" > > > > main = main2 > > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners From hanche at math.ntnu.no Tue Jun 14 14:47:08 2016 From: hanche at math.ntnu.no (Harald Hanche-Olsen) Date: Tue, 14 Jun 2016 14:47:08 +0000 Subject: [Haskell-beginners] State Monad in constant space? In-Reply-To: <575DCFE9.7070904@web.de> References: <575DCFE9.7070904@web.de> Message-ID: Being an absolute beginner myself, I should probably refrain from trying to answer this one, but since no one else did, I?ll give it a shot: I assume it all comes down to laziness. The gargantuan expression will not be built all at once, but rather the beginning of it is built and evaluated. The result of evaluating the leftmost part will (hopefully) be simpler than the expression that defined it! In any case, that expression is now safely discarded, a bit more of the expression is built, and the evaluation can proceed. The principle shouldn?t be all that different from any tail recursive function application, really. ? Harald On 12 June 2016 at 23:11:32, martin (martin.drautzburg at web.de(mailto:martin.drautzburg at web.de)) wrote: > Hello all, > > the State Monad wraps around a computation s -> (s,a). Inside a do block I am actually assembling such a computation. > Now when I do this many times, i.e. in a recursice call, I am builing a huge expression > > m a >>= (\a -> mb) >>= (\b -> mc) ... > > The result of this expression is a function s -> (s,a). But I cannot see how the space for this expression can be > reclaimed, and how it could ever run in constant space. Once I call runState and I provide an initial s, I have some > hope, but before? > > How is this supposed to work? How do I avoid allocating space for this huge expression? From toad3k at gmail.com Tue Jun 14 15:27:08 2016 From: toad3k at gmail.com (David McBride) Date: Tue, 14 Jun 2016 11:27:08 -0400 Subject: [Haskell-beginners] State Monad in constant space? In-Reply-To: <575DCFE9.7070904@web.de> References: <575DCFE9.7070904@web.de> Message-ID: Remember that StateT (and by extension, State) is just a newtype wrapper. Newtypes have no runtime cost. In this case it simply contains a function. Constructing an expression full of binds against StateT before supplying an argument via runStateT is no different than combining several functions and supplying their argument later. As far as memory usage is concerned, there is one caveat. The state variable that is returned after every bind can build up thunks if it is altered but not fully evaluated in any given step. This could lead to a memory link as operations are tacked onto the state variable you supplied. If you use Control.Monad.State.Strict, that variable will be evaluated whether you use it or not, preventing laziness from building up thunks. On Sun, Jun 12, 2016 at 5:11 PM, martin wrote: > Hello all, > > the State Monad wraps around a computation s -> (s,a). Inside a do block I > am actually assembling such a computation. > Now when I do this many times, i.e. in a recursice call, I am builing a > huge expression > > m a >>= (\a -> mb) >>= (\b -> mc) ... > > The result of this expression is a function s -> (s,a). But I cannot see > how the space for this expression can be > reclaimed, and how it could ever run in constant space. Once I call > runState and I provide an initial s, I have some > hope, but before? > > How is this supposed to work? How do I avoid allocating space for this > huge expression? > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From imantc at gmail.com Thu Jun 16 08:04:19 2016 From: imantc at gmail.com (Imants Cekusins) Date: Thu, 16 Jun 2016 10:04:19 +0200 Subject: [Haskell-beginners] default(Int) Message-ID: default(Int) allows to use integers anywhere in this module without specifying their ambiguous type each time, like this: (3::Int) https://www.haskell.org/tutorial/numbers.html section 10.4 some other default types may be specified too somehow I was not aware of this -------------- next part -------------- An HTML attachment was scrubbed... URL: From ky3 at atamo.com Thu Jun 16 09:42:06 2016 From: ky3 at atamo.com (Kim-Ee Yeoh) Date: Thu, 16 Jun 2016 16:42:06 +0700 Subject: [Haskell-beginners] default(Int) In-Reply-To: References: Message-ID: It is true that ambiguous types cause time-wasting frustration for many a beginner. The link that Imants gave helps clarify matters: https://www.haskell.org/tutorial/numbers.html Even better is the link to the Haskell report given at the end: https://www.haskell.org/onlinereport/decls.html#default-decls On Thursday, June 16, 2016, Imants Cekusins wrote: > default(Int) > > allows to use integers anywhere in this module without specifying their > ambiguous type each time, like this: (3::Int) > > https://www.haskell.org/tutorial/numbers.html > section 10.4 > > some other default types may be specified too > somehow I was not aware of this > -- -- Kim-Ee -------------- next part -------------- An HTML attachment was scrubbed... URL: From Graham.Hutton at nottingham.ac.uk Tue Jun 21 14:05:25 2016 From: Graham.Hutton at nottingham.ac.uk (Graham Hutton) Date: Tue, 21 Jun 2016 14:05:25 +0000 Subject: [Haskell-beginners] Programming in Haskell - 2nd Edition Message-ID: Dear all, I'm delighted to announce that the 2nd edition of Programming in Haskell will be published in August 2016! The new edition has been extensively updated and expanded to include recent and more advanced features of Haskell, new examples and exercises, selected solutions, and freely downloadable lecture slides and example code. Further details, including how to preorder and obtain inspection copies, are provided below. Best wishes, Graham ================================================================= *** BOOK ANNOUNCEMENT *** Programming in Haskell - 2nd Edition Graham Hutton, University of Nottingham Cambridge University Press, August 2016 320 pages, 120 exercises, ISBN 9781316626221 http://tinyurl.com/PIH-2e ================================================================= DESCRIPTION: Haskell is a purely functional language that allows programmers to rapidly develop clear, concise, and correct software. The language has grown in popularity in recent years, both in teaching and in industry. This book is based on the author's experience of teaching Haskell for more than twenty years. All concepts are explained from first principles and no programming experience is required, making this book accessible to a broad spectrum of readers. While Part I focuses on basic concepts, Part II introduces the reader to more advanced topics. This new edition has been extensively updated and expanded to include recent and more advanced features of Haskell, new examples and exercises, selected solutions, and freely downloadable lecture slides and example code. The presentation is clean and simple, while also being fully compliant with the latest version of the language, including recent changes concerning applicative, monadic, foldable, and traversable types. ================================================================= CONTENTS: Foreword Preface Part I. Basic Concepts: 1. Introduction 2. First steps 3. Types and classes 4. Defining functions 5. List comprehensions 6. Recursive functions 7. Higher-order functions 8. Declaring types and classes 9. The countdown problem Part II. Going Further: 10. Interactive programming 11. Unbeatable tic-tac-toe 12. Monads and more 13. Monadic parsing 14. Foldables and friends 15. Lazy evaluation 16. Reasoning about programs 17. Calculating compilers Appendix A. Selected solutions Appendix B. Standard prelude Bibliography Index ================================================================= AUTHOR: Graham Hutton is Professor of Computer Science at the University of Nottingham. He has taught Haskell to thousands of students and received numerous best lecturer awards. Hutton has served as an editor of the Journal of Functional Programming, Chair of the Haskell Symposium and the International Conference on Functional Programming, and Vice-Chair of the ACM Special Interest Group on Programming Languages, and he is an ACM Distinguished Scientist. ================================================================= FURTHER DETAILS: The following web page includes details for how the book can be preordered, and how lecturers can obtain inspection copies: http://tinyurl.com/PIH-2e ================================================================= This message and any attachment are intended solely for the addressee and may contain confidential information. If you have received this message in error, please send it back to me, and immediately delete it. Please do not use, copy or disclose the information contained in this message or in any attachment. Any views or opinions expressed by the author of this email do not necessarily reflect the views of the University of Nottingham. This message has been checked for viruses but the contents of an attachment may still contain software viruses which could damage your computer system, you are advised to perform your own checks. Email communications with the University of Nottingham may be monitored as permitted by UK legislation. From matthewjwilliams101 at gmail.com Tue Jun 21 16:39:37 2016 From: matthewjwilliams101 at gmail.com (MJ Williams) Date: Tue, 21 Jun 2016 17:39:37 +0100 Subject: [Haskell-beginners] Programming in Haskell - 2nd Edition In-Reply-To: References: Message-ID: Hello Graham, Will the book be available on Amazon Kindle? Matt On 21/06/2016, Graham Hutton wrote: > Dear all, > > I'm delighted to announce that the 2nd edition of Programming > in Haskell will be published in August 2016! The new edition > has been extensively updated and expanded to include recent and > more advanced features of Haskell, new examples and exercises, > selected solutions, and freely downloadable lecture slides and > example code. Further details, including how to preorder and > obtain inspection copies, are provided below. > > Best wishes, > > Graham > > ================================================================= > > *** BOOK ANNOUNCEMENT *** > > Programming in Haskell - 2nd Edition > > Graham Hutton, University of Nottingham > > Cambridge University Press, August 2016 > > 320 pages, 120 exercises, ISBN 9781316626221 > > http://tinyurl.com/PIH-2e > > ================================================================= > > DESCRIPTION: > > Haskell is a purely functional language that allows programmers > to rapidly develop clear, concise, and correct software. The > language has grown in popularity in recent years, both in teaching > and in industry. This book is based on the author's experience > of teaching Haskell for more than twenty years. All concepts > are explained from first principles and no programming experience > is required, making this book accessible to a broad spectrum > of readers. While Part I focuses on basic concepts, Part II > introduces the reader to more advanced topics. > > This new edition has been extensively updated and expanded to > include recent and more advanced features of Haskell, new examples > and exercises, selected solutions, and freely downloadable lecture > slides and example code. The presentation is clean and simple, > while also being fully compliant with the latest version of > the language, including recent changes concerning applicative, > monadic, foldable, and traversable types. > > ================================================================= > > CONTENTS: > > Foreword > Preface > Part I. Basic Concepts: > 1. Introduction > 2. First steps > 3. Types and classes > 4. Defining functions > 5. List comprehensions > 6. Recursive functions > 7. Higher-order functions > 8. Declaring types and classes > 9. The countdown problem > Part II. Going Further: > 10. Interactive programming > 11. Unbeatable tic-tac-toe > 12. Monads and more > 13. Monadic parsing > 14. Foldables and friends > 15. Lazy evaluation > 16. Reasoning about programs > 17. Calculating compilers > Appendix A. Selected solutions > Appendix B. Standard prelude > Bibliography > Index > > ================================================================= > > AUTHOR: > > Graham Hutton is Professor of Computer Science at the University > of Nottingham. He has taught Haskell to thousands of students > and received numerous best lecturer awards. Hutton has served as > an editor of the Journal of Functional Programming, Chair of the > Haskell Symposium and the International Conference on Functional > Programming, and Vice-Chair of the ACM Special Interest Group on > Programming Languages, and he is an ACM Distinguished Scientist. > > ================================================================= > > FURTHER DETAILS: > > The following web page includes details for how the book can be > preordered, and how lecturers can obtain inspection copies: > > http://tinyurl.com/PIH-2e > > ================================================================= > > > > > This message and any attachment are intended solely for the addressee > and may contain confidential information. If you have received this > message in error, please send it back to me, and immediately delete it. > > Please do not use, copy or disclose the information contained in this > message or in any attachment. Any views or opinions expressed by the > author of this email do not necessarily reflect the views of the > University of Nottingham. > > This message has been checked for viruses but the contents of an > attachment may still contain software viruses which could damage your > computer system, you are advised to perform your own checks. Email > communications with the University of Nottingham may be monitored as > permitted by UK legislation. > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > From twashing at gmail.com Thu Jun 23 07:58:24 2016 From: twashing at gmail.com (Timothy Washington) Date: Thu, 23 Jun 2016 00:58:24 -0700 Subject: [Haskell-beginners] Howto reverse a Data.Array Message-ID: I'm still trying to get an intuitive understanding of Haskell's Data.Array , in contrast to Data.List or Data.Vector. I very much want a nested array (a matrix), where the parent list (or rows) are reversed. But neither *A.array* nor *A.istArray* allow indicies to be reversed in their constructors, nor the list comprehensions that generate the elements The only reason I'm using an array, is for the *A.//* function (operating on a matrix). Otherwise, I'd use Data.Vector which does have a reverse function, but a less powerful *V.//* , that doesn't accept coordinates in a matrix. Can I reverse a Data.Array? If not, then why. Thanks Tim -------------- next part -------------- An HTML attachment was scrubbed... URL: From toad3k at gmail.com Thu Jun 23 14:41:22 2016 From: toad3k at gmail.com (David McBride) Date: Thu, 23 Jun 2016 10:41:22 -0400 Subject: [Haskell-beginners] Howto reverse a Data.Array In-Reply-To: References: Message-ID: The problem isn't with array, but rather your index. Ix instances are always sorted in ascending order, as you might imagine. You can however, use your own index in arrays and they can be indexed in whatever order you like. {-# LANGUAGE GeneralizedNewtypeDeriving #-} import Data.Array import Data.Ix newtype MyIx = MyIx Int deriving (Eq, Num, Show) instance Ord MyIx where compare (MyIx a) (MyIx b) = case compare a b of LT -> GT GT -> LT EQ -> EQ instance Ix MyIx where range (MyIx a, MyIx b) = map MyIx $ reverse [b..a] index (MyIx a, MyIx b) (MyIx c) = a - c inRange (MyIx a, MyIx b) (MyIx c) = c <= a && c >= b blah :: Array MyIx Char blah = array (3,0) [(0,'a'),(1,'b'),(2,'c'),(3,'d')] Warning: I only very lightly tested the above code. You can mix your index and normal indexes to get the row / col ordering you are hoping for. blah2 :: [((MyIx, Int), Char)] -> Array (MyIx, Int) Char blah2 = array ((3,0),(0,3)) Finally, if you are really looking for something that is designed to be a matrix, you might try one of several libraries that are out there, like hmatrix. Hopefully this helps. On Thu, Jun 23, 2016 at 3:58 AM, Timothy Washington wrote: > I'm still trying to get an intuitive understanding of Haskell's Data.Array > , > in contrast to Data.List or Data.Vector. > > I very much want a nested array (a matrix), where the parent list (or > rows) are reversed. But neither *A.array* nor *A.istArray* allow indicies > to be reversed in their constructors, nor the list comprehensions that > generate the elements > > The only reason I'm using an array, is for the *A.//* function (operating > on a matrix). Otherwise, I'd use Data.Vector > > which does have a reverse function, but a less powerful *V.//* , that > doesn't accept coordinates in a matrix. > > Can I reverse a Data.Array? If not, then why. > > > Thanks > Tim > > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From rein.henrichs at gmail.com Fri Jun 24 22:54:22 2016 From: rein.henrichs at gmail.com (Rein Henrichs) Date: Fri, 24 Jun 2016 22:54:22 +0000 Subject: [Haskell-beginners] Functions as containers; implications on being a Monad ((->) r) In-Reply-To: References: <87k2i4x599.fsf@chladni.i-did-not-set--mail-host-address--so-tickle-me> Message-ID: Don't be led astray by leaky analogies. A Functor is not a container. *Some* Functor instances are* like* containers. When this analogy stops working, discard it and think about the problem directly. Like any other typeclass, Functor is just a collection of methods and laws[1]; its instances are just types which have law abiding implementations of the methods. Knowing the type of fmap and its laws, we know what it means for ((->) r) to be an instance: it means that we can define fmap :: (a -> b) -> f a -> f b for f = ((->) r) and prove that it satisfies the laws. Substituting for f, we have: fmap :: (a -> b) -> (r -> a) -> (r -> b) By alpha equivalence, we can rename this to fmap :: (b -> c) -> (a -> b) -> a -> c and immediately we find a candidate implementation in function composition, (.) :: (b -> c) -> (a -> b) -> a -> c: fmap f g = f . g Now we must prove that this implementation is law abiding. I'll show a proof for the first law, fmap id = id, with assistance from a few definitions: 1) f . g = \x -> f (g x) 2) id x = x 3) \x -> f x = f fmap id f = id . f {- definition of fmap -} = \x -> id (f x) {- by (1) -} = \x -> f x {- by (2) -} = f {- by (3) -} = id f {- by (2) -} Thus we have fmap id f = id f and (by eta reduction) fmap id = id. Try to prove the second law for yourself! Once you've proven it, you know that ((->) r) is an instance of Functor where fmap = (.)[2]. If you do the same for Applicative and Monad then you will know exactly how ((->) r) is a Functor, an Applicative, and a Monad. Then you can experiment by applying the typeclass methods to functions to see what the practical value of these definitions is. For example. the Applicative instance lets you plumb a shared argument to a number of functions. Here's a contrived example: > (++) <$> map toUpper <*> reverse $ "Hello" "HELLOolleH" -R [1] The laws are not really a part of the typeclass proper (i.e., the compiler doesn't know anything about them), but developers need to ensure that their instances are law abiding so that they behave as expected. [2]: Actually, it turns out that one only needs to prove the first law for fmap because the second law is implied by the first, but that's a topic for another day! On Sat, Jun 4, 2016 at 5:11 PM Gesh wrote: > On 2016-06-04 19:56, Daniel Bergey wrote: > > I think "a functor is a container" is not so helpful. It works OK for > > Maybe and List, but it doesn't seem helpful in understanding Either, > > Reader, Writer, State, Continuation, promises. > This is correct. However, a large class of types form what are called > "Representable Functors". > These include Lists, Trees, ((->) r), etc. > > A representable functor is any type f with an isomorphism `(f a ~ r -> > a)` for some r. > For example, `Stream a ~ Natural -> a` under the isomorphism: > > toFunction xs = \i -> xs !! i > > toList f = fromList $ map f [0..] > > I *think* it's the case that for (r ->), there isn't anything we can do > > with the Monad instance that we can't do with Applicative. If someone > > can confirm or refute that, I'd appreciate it. That's of course not > > true in general for other monads. > Indeed, for any representable functor, this all follows from the fact > that we can write a lawful > join from Reader's <*>. Letting `join m = flip ($) <*> m`, we have: > > (join . pure) x = \r -> ($ r) (const x r) = \r -> x $ r = x > > (join . fmap pure) x = \r -> ($ r) ((pure . x) r) = \r -> (const (x > r)) r = \r -> x r = x > > (join . fmap join) x = \r -> ($ r) ((join . x) r) = \r -> join (x r) > r = \r -> (\s -> ($s) (x r s)) r > > = \r -> x r r r = \r -> ($r) (\s -> x s s) r = join (\s -> ($s) (x > s)) = (join . join) x > > Hence, given the applicative instance for Reader, we obtain the Monad > instance for free. > Therefore, working under the isomorphism, we have the same for any > representable functor. > > In particular, this gives that Stream is a Monad, where return gives the > constant stream and > join takes the diagonal of a stream of streams. > > Again, as noted, this is more or less the only way in which the > "Functors/Applicatives/Monads are nice/nicer/nicest containers" analogy > works. > There are more things in heaven and earth than are described in that > analogy, but it's a start. > > Hope this helps, and that it lacks errors/misleading material, > Gesh > P.S. Code for working with representable functors can be found in > representable-functors. > Code for working with Streams can be found in streams. Both are on Hackage. > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From frederic-emmanuel.picca at synchrotron-soleil.fr Mon Jun 27 16:49:46 2016 From: frederic-emmanuel.picca at synchrotron-soleil.fr (PICCA Frederic-Emmanuel) Date: Mon, 27 Jun 2016 16:49:46 +0000 Subject: [Haskell-beginners] Strorable and incomplete type Message-ID: Hello, I would like to use Storable and declare an instance for a struct available in a C library instance Storable Parameter where sizeOf _ = #{size HklParameter} peek ptr = alloca $ \pmin -> alloca $ \pmax -> do cname <- c_hkl_parameter_name_get ptr name <- peekCString cname value <- c_hkl_parameter_value_get ptr unit c_hkl_parameter_min_max_get ptr pmin pmax unit min <- peek pmin max <- peek pmax return (Parameter name value (Range min max)) but when I try to compile this, I get this error message C.hsc:507:15: error: invalid application of ‘sizeof’ to incomplete type ‘HklParameter’ Indeed the C library do not expose this struct internal. So I would like to know how to handle this kind of C struct with Storable. thanks for your help Frédéric From martin.drautzburg at web.de Tue Jun 28 18:39:46 2016 From: martin.drautzburg at web.de (martin) Date: Tue, 28 Jun 2016 20:39:46 +0200 Subject: [Haskell-beginners] RDBMS like references? Message-ID: <5772C472.5060508@web.de> Hello all, I recently tried to model "Items", where an Item can either be inside another Item or at a certain location. I started like this: data Location i l = At l | In (Item i l) deriving (Eq, Show) data Item i l = Itm i (Location i l) deriving (Eq, Show) type ItemDb i l = [Item i l] ex_itemdb = let i1 = Itm 1 (At "a") i2 = Itm 2 (In i1) in [i1, i2] Now I wanted to move Item 1 to a different location using this code: moved = fmap f ex_itemdb where f (Itm 1 (At "a")) = (Itm 1 (At "b")) f x = x Not this does not do what I want. I get -- *Main> ex_itemdb -- [Itm 1 (At "a"),Itm 2 (In (Itm 1 (At "a")))] -- *Main> moved -- [Itm 1 (At "b"),Itm 2 (In (Itm 1 (At "a")))] While Item 1 has moved to "b" Item 2 still claims to be in an "Itm 1 (At "a")". I understand what's going on here and coming from a DB background I can see that the redundant data is the root of the problem. I can model this in a relational way such that the redundancy is avoided. But maybe there is a more haskellish/idiomatic way to acomplish this. Is there? From tanuki at gmail.com Tue Jun 28 21:26:49 2016 From: tanuki at gmail.com (Theodore Lief Gannon) Date: Tue, 28 Jun 2016 14:26:49 -0700 Subject: [Haskell-beginners] RDBMS like references? In-Reply-To: <5772C472.5060508@web.de> References: <5772C472.5060508@web.de> Message-ID: Sometimes relational is the way to go, but it's always worth looking for other options. :) The idiomatic preference, I think, would be to separate the nesting structure from the object data. The item containment graph sounds like a RoseTree, and since location is always inherited, that can just be a Map. import qualified Data.Map as M data Rose a = Rose a [Rose a] deriving (Eq, Show) data Item a = Item a deriving (Eq, Show) type ItemGraph a = Rose (Item a) type ItemDB k a = M.Map k (ItemGraph a) >>> let ex_itemdb = M.fromList [("a", Rose (Item 1) [Rose (Item 2) []])] >>> M.lookup "a" ex_itemdb Just (Rose (Item 1) [Rose (Item 2) []]) >>> let roseContains i (Rose x xs) = i == x || any (roseContains i) xs >>> let isItemAt i l idb = maybe False id $ roseContains i <$> M.lookup l idb >>> isItemAt (Item 2) "a" ex_itemdb True >>> let swapLoc l1 l2 idb = let {i1 = M.lookup l1 idb; i2 = M.lookup l2 idb} in maybe (M.delete l1) (M.insert l1) i2 . maybe (M.delete l2) (M.insert l2) i1 $ idb >>> let moved = swapLoc "a" "b" ex_itemdb >>> isItemAt (Item 2) "a" moved False >>> moved fromList [("b",Rose (Item 1) [Rose (Item 2) []])] There are quite a few unfinished pieces here, but hopefully it gets you thinking in new directions! On Tue, Jun 28, 2016 at 11:39 AM, martin wrote: > Hello all, > > I recently tried to model "Items", where an Item can either be inside > another Item or at a certain location. I started > like this: > > data Location i l = At l > | In (Item i l) > deriving (Eq, Show) > > data Item i l = Itm i (Location i l) > deriving (Eq, Show) > > type ItemDb i l = [Item i l] > > ex_itemdb = let i1 = Itm 1 (At "a") > i2 = Itm 2 (In i1) > in [i1, i2] > > Now I wanted to move Item 1 to a different location using this code: > > moved = fmap f ex_itemdb > where > f (Itm 1 (At "a")) = (Itm 1 (At "b")) > f x = x > > Not this does not do what I want. I get > > -- *Main> ex_itemdb > -- [Itm 1 (At "a"),Itm 2 (In (Itm 1 (At "a")))] > > -- *Main> moved > -- [Itm 1 (At "b"),Itm 2 (In (Itm 1 (At "a")))] > > While Item 1 has moved to "b" Item 2 still claims to be in an "Itm 1 (At > "a")". I understand what's going on here and > coming from a DB background I can see that the redundant data is the root > of the problem. > > I can model this in a relational way such that the redundancy is avoided. > But maybe there is a more haskellish/idiomatic > way to acomplish this. > > Is there? > > _______________________________________________ > Beginners mailing list > Beginners at haskell.org > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners > -------------- next part -------------- An HTML attachment was scrubbed... URL: From tanuki at gmail.com Tue Jun 28 22:10:22 2016 From: tanuki at gmail.com (Theodore Lief Gannon) Date: Tue, 28 Jun 2016 15:10:22 -0700 Subject: [Haskell-beginners] RDBMS like references? In-Reply-To: References: <5772C472.5060508@web.de> Message-ID: Another possibility would be to keep your definition for Location, but switch to: data Item a = Item a type ItemDB = Map Item Location ...and use a recursive lookup to find the location of an item contained within another. This is quite a bit simpler, but whether it's preferable probably depends on whether your more common lookup is "where is item x?" vs. "what's at location y?" On Jun 28, 2016 2:26 PM, "Theodore Lief Gannon" wrote: > Sometimes relational is the way to go, but it's always worth looking for > other options. :) The idiomatic preference, I think, would be to separate > the nesting structure from the object data. The item containment graph > sounds like a RoseTree, and since location is always inherited, that can > just be a Map. > > import qualified Data.Map as M > data Rose a = Rose a [Rose a] deriving (Eq, Show) > data Item a = Item a deriving (Eq, Show) > type ItemGraph a = Rose (Item a) > type ItemDB k a = M.Map k (ItemGraph a) > > >>> let ex_itemdb = M.fromList [("a", Rose (Item 1) [Rose (Item 2) []])] > >>> M.lookup "a" ex_itemdb > Just (Rose (Item 1) [Rose (Item 2) []]) > > >>> let roseContains i (Rose x xs) = i == x || any (roseContains i) xs > >>> let isItemAt i l idb = maybe False id $ roseContains i <$> M.lookup l > idb > >>> isItemAt (Item 2) "a" ex_itemdb > True > > >>> let swapLoc l1 l2 idb = let {i1 = M.lookup l1 idb; i2 = M.lookup l2 > idb} in maybe (M.delete l1) (M.insert l1) i2 . maybe (M.delete l2) > (M.insert l2) i1 $ idb > >>> let moved = swapLoc "a" "b" ex_itemdb > >>> isItemAt (Item 2) "a" moved > False > >>> moved > fromList [("b",Rose (Item 1) [Rose (Item 2) []])] > > There are quite a few unfinished pieces here, but hopefully it gets you > thinking in new directions! > > On Tue, Jun 28, 2016 at 11:39 AM, martin wrote: > >> Hello all, >> >> I recently tried to model "Items", where an Item can either be inside >> another Item or at a certain location. I started >> like this: >> >> data Location i l = At l >> | In (Item i l) >> deriving (Eq, Show) >> >> data Item i l = Itm i (Location i l) >> deriving (Eq, Show) >> >> type ItemDb i l = [Item i l] >> >> ex_itemdb = let i1 = Itm 1 (At "a") >> i2 = Itm 2 (In i1) >> in [i1, i2] >> >> Now I wanted to move Item 1 to a different location using this code: >> >> moved = fmap f ex_itemdb >> where >> f (Itm 1 (At "a")) = (Itm 1 (At "b")) >> f x = x >> >> Not this does not do what I want. I get >> >> -- *Main> ex_itemdb >> -- [Itm 1 (At "a"),Itm 2 (In (Itm 1 (At "a")))] >> >> -- *Main> moved >> -- [Itm 1 (At "b"),Itm 2 (In (Itm 1 (At "a")))] >> >> While Item 1 has moved to "b" Item 2 still claims to be in an "Itm 1 (At >> "a")". I understand what's going on here and >> coming from a DB background I can see that the redundant data is the root >> of the problem. >> >> I can model this in a relational way such that the redundancy is avoided. >> But maybe there is a more haskellish/idiomatic >> way to acomplish this. >> >> Is there? >> >> _______________________________________________ >> Beginners mailing list >> Beginners at haskell.org >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners >> > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From jolivetdesonte at yahoo.com Wed Jun 29 03:39:23 2016 From: jolivetdesonte at yahoo.com (Desonte Jolivet) Date: Wed, 29 Jun 2016 03:39:23 +0000 (UTC) Subject: [Haskell-beginners] Generating Infinite List of Fibonacci Numbers References: <2139750997.643950.1467171563397.JavaMail.yahoo.ref@mail.yahoo.com> Message-ID: <2139750997.643950.1467171563397.JavaMail.yahoo@mail.yahoo.com> Hi, Problem: I would like to generate an infinite list of Fibonacci numbers. Although the below code does not work. fibs :: [Integer]fibs = 0 : 1 : [ n | x <-[2..], let n = ((fibs !! x-1) + (fibs !! x-2))] Thought: I'm assuming that I'm ignorant on how ranges/generators work with a list comprehension, which is why this code is not working. ghci output: *Main> fibs !! 01*Main> fibs !! 12*Main> fibs !! 2  When I try and access the third element in the list ghci simply stalls. Can someone please give me a little more insight on why my code is not working. Thanks in advance. drjoliv -------------- next part -------------- An HTML attachment was scrubbed... URL: From bo at ct.de Wed Jun 29 06:27:53 2016 From: bo at ct.de (=?UTF-8?Q?Harald_B=c3=b6geholz?=) Date: Wed, 29 Jun 2016 08:27:53 +0200 Subject: [Haskell-beginners] Generating Infinite List of Fibonacci Numbers In-Reply-To: <2139750997.643950.1467171563397.JavaMail.yahoo@mail.yahoo.com> References: <2139750997.643950.1467171563397.JavaMail.yahoo.ref@mail.yahoo.com> <2139750997.643950.1467171563397.JavaMail.yahoo@mail.yahoo.com> Message-ID: Am 29.06.16 um 05:39 schrieb Desonte Jolivet: > > Hi, > > Problem: I would like to generate an infinite list of Fibonacci numbers. Although the below code does not work. > > fibs :: [Integer]fibs = 0 : 1 : [ n | x <-[2..], let n = ((fibs !! x-1) + (fibs !! x-2))] > > Thought: I'm assuming that I'm ignorant on how ranges/generators work with a list comprehension, which is why this code is not working. > > ghci output: > *Main> fibs !! 01*Main> fibs !! 12*Main> fibs !! 2 > When I try and access the third element in the list ghci simply stalls. > Can someone please give me a little more insight on why my code is not working. You need to insert parentheses: Prelude> let fibs = 0 : 1 : [ n | x <-[2..], let n = ((fibs !! (x-1)) + (fibs !! (x-2)))] Prelude> take 50 fibs [0,1,1,2,3,5,8,13,21,34,55,89,144,233,377,610,987,1597,2584,4181,6765,10946,17711,28657,46368,75025,121393,196418,317811,514229,832040,1346269,2178309,3524578,5702887,9227465,14930352,24157817,39088169,63245986,102334155,165580141,267914296,433494437,701408733,1134903170,1836311903,2971215073,4807526976,7778742049] Btw a probably more efficient way to generate this list is Prelude> let fibs' = 0 : 1 : zipWith (+) fibs' (tail fibs') Prelude> take 50 fibs' [0,1,1,2,3,5,8,13,21,34,55,89,144,233,377,610,987,1597,2584,4181,6765,10946,17711,28657,46368,75025,121393,196418,317811,514229,832040,1346269,2178309,3524578,5702887,9227465,14930352,24157817,39088169,63245986,102334155,165580141,267914296,433494437,701408733,1134903170,1836311903,2971215073,4807526976,7778742049] Cheers Harald -- Harald Bögeholz (PGP key available from servers) Redaktion c't Tel.: +49 511 5352-300 Fax: +49 511 5352-417 http://www.ct.de/ int f[9814],b,c=9814,g,i;long a=1e4,d,e,h; main(){for(;b=c,c-=14;i=printf("%04d",e+d/a),e=d%a) while(g=--b*2)d=h*b+a*(i?f[b]:a/5),h=d/--g,f[b]=d%g;} (Arndt/Haenel) Affe Apfel Vergaser /*Heise Medien GmbH & Co. KG * Karl-Wiechert-Allee 10 * 30625 Hannover Registergericht: Amtsgericht Hannover HRA 26709 Persönlich haftende Gesellschafterin: Heise Medien Geschäftsführung GmbH Registergericht: Amtsgericht Hannover, HRB 60405 Geschäftsführer: Ansgar Heise, Dr. Alfons Schräder*/ From dennis.raddle at gmail.com Wed Jun 29 08:20:47 2016 From: dennis.raddle at gmail.com (Dennis Raddle) Date: Wed, 29 Jun 2016 01:20:47 -0700 Subject: [Haskell-beginners] error writing FilePath to text file Message-ID: Hello, I wrote a program that reads filenames using System.Directory "listDirectory", does some tests on them, and writes certain file names (as read into a FilePath variable by listDirectory) to a text file, which I later parse with Parsec. I am getting an error on writing to the text file: commitBuffer: invalid argument (invalid character) What can I do about this? If I am reading some kind of unusual characters from the FilePath, I want to choose some way of writing them so that the resulting file can still be parsed by Text.Parsec.ByteString. I hope that I can still rely on the "space" parser to find CR and LF, and don't want any other surprises. D -------------- next part -------------- An HTML attachment was scrubbed... URL: From michael at snoyman.com Wed Jun 29 08:24:35 2016 From: michael at snoyman.com (Michael Snoyman) Date: Wed, 29 Jun 2016 11:24:35 +0300 Subject: [Haskell-beginners] error writing FilePath to text file In-Reply-To: References: Message-ID: On Wed, Jun 29, 2016 at 11:20 AM, Dennis Raddle wrote: > Hello, I wrote a program that reads filenames using System.Directory > "listDirectory", does some tests on them, and writes certain file names (as > read into a FilePath variable by listDirectory) to a text file, which I > later parse with Parsec. I am getting an error on writing to the text file: > > commitBuffer: invalid argument (invalid character) > > What can I do about this? If I am reading some kind of unusual characters > from the FilePath, I want to choose some way of writing them so that the > resulting file can still be parsed by Text.Parsec.ByteString. I hope that I > can still rely on the "space" parser to find CR and LF, and don't want any > other surprises. > > D > > I'd recommend being explicit about the character encoding you're using, and using the bytestring API for the I/O itself. As an example: import qualified Data.Text.Lazy as TL import qualified Data.Text.Lazy.Encoding as TL import qualified Data.ByteString.Lazy as L writeFileUtf8 :: FilePath -> String -> IO () writeFileUtf8 fp str = L.writeFile fp (TL.encodeUtf8 (TL.pack str)) The default handling of character encodings is reliant on environment variables, which IME makes the textual file writing functions notoriously fragile. Michael -------------- next part -------------- An HTML attachment was scrubbed... URL: From dennis.raddle at gmail.com Wed Jun 29 08:31:25 2016 From: dennis.raddle at gmail.com (Dennis Raddle) Date: Wed, 29 Jun 2016 01:31:25 -0700 Subject: [Haskell-beginners] error writing FilePath to text file In-Reply-To: References: Message-ID: Thanks. ​I don't know if I was clear that I'm writing the characters of the FilePath to a file. I could use something like: writeFilePaths :: FilePath -> [FilePath] -> IO () writeFilePaths fileToWrite fps = ... The ByteStrings are for reading the files generated by the above and parsing with Text.Parsec.ByteString, for efficiency (these are many megabytes of text) D -------------- next part -------------- An HTML attachment was scrubbed... URL: From michael at snoyman.com Wed Jun 29 08:34:39 2016 From: michael at snoyman.com (Michael Snoyman) Date: Wed, 29 Jun 2016 11:34:39 +0300 Subject: [Haskell-beginners] error writing FilePath to text file In-Reply-To: References: Message-ID: On Wed, Jun 29, 2016 at 11:31 AM, Dennis Raddle wrote: > Thanks. ​I don't know if I was clear that I'm writing the characters of > the FilePath to a file. I could use something like: > > writeFilePaths :: FilePath -> [FilePath] -> IO () > writeFilePaths fileToWrite fps = ... > > The ByteStrings are for reading the files generated by the above and > parsing with Text.Parsec.ByteString, for efficiency (these are many > megabytes of text) > > D > > > A FilePath is just a type synonym for a String, so the same caveats will apply to both. I'm guessing that you're dealing with some file paths that have non-ASCII characters in them, and you have some locale environment variables set that do not support UTF8. You can try rerunning your program as-is with: export LANG=en_US.UTF-8 in the shell (assuming you're on a POSIX system, Windows will behave differently). Michael -------------- next part -------------- An HTML attachment was scrubbed... URL: