Examples for Control.Lens.Plated?

Hello Cafe, I'm considering porting some of my code that uses uniplate to lens. But Control.Lens.Plated is giving me headaches. So I'm looking for remedy. Has anyone used it and willing to share examples? I hope that seeing some of the combinators in action would help me understand the type signatures and documentation. What I'm particularly interested in is the following: 1) implementation of something like transformBi and rewriteBi using lens 2) usage of *On, *Off and *OnOff combinators (e.g., transformMOn, transformMOff, transformMOnOff). What I want to understand is the difference between the 3 variants. Also, what does it mean to "Transform every element in the tree in a region indicated by a supplied Traversal" and how exactly does the traversal define the region. 3) any recursive tree traversals/transformations using Plated that stop the recursion at a certain point (e.g., upon seeing a certain constructor) I hope this isn't too vague, but, please, let me know if it is. /Andrey

+1 I've been missing such examples for a long time too. Michał Original Message From: Andrey Chudnov Sent: Wednesday, September 2, 2015 7:44 PM To: haskell-cafe Subject: [Haskell-cafe] Examples for Control.Lens.Plated? Hello Cafe, I'm considering porting some of my code that uses uniplate to lens. But Control.Lens.Plated is giving me headaches. So I'm looking for remedy. Has anyone used it and willing to share examples? I hope that seeing some of the combinators in action would help me understand the type signatures and documentation. What I'm particularly interested in is the following: 1) implementation of something like transformBi and rewriteBi using lens 2) usage of *On, *Off and *OnOff combinators (e.g., transformMOn, transformMOff, transformMOnOff). What I want to understand is the difference between the 3 variants. Also, what does it mean to "Transform every element in the tree in a region indicated by a supplied Traversal" and how exactly does the traversal define the region. 3) any recursive tree traversals/transformations using Plated that stop the recursion at a certain point (e.g., upon seeing a certain constructor) I hope this isn't too vague, but, please, let me know if it is. /Andrey _______________________________________________ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe

I thought I'd add an example of what I'm trying to do and what I think transformMOnOff might be very helpful with... that is, if I only knew how to use it. So suppose I have two mutrec data types,
data A = A [A] | B B | I Int data B = B [A]
Suppose I want to write a function
incrementByNestingDepth :: A -> A
that would traverse the tree and increment all the I's by their nesting depth in B, e.g.
incrementByNestingDepth (A [I 1, I 3, B [ A [I 2], B [I 1]]]) = A [I 1, I 3, B [A [I 3], B [I 3]]]
I could write that with just recursion on A and B, which could get tedious if I had several datatypes with 20 constructors each. Or I could use uniplate. But that's still quite tedious:
incrementByNestingDepth a = runState (incrementM a) 0 incrementM :: A -> State Int A incrementM a = case a of I i -> liftM (A . (i +)) get B b->liftM B $ descendBiM incrementM b _ -> descendM incrementM a
The code isn't much smaller than for a handwritten traversal and you could imagine (or take my word for it) that one still doesn't see a lot of saved space using uniplate with more elaborate examples. Now, don't get me wrong: I'm not saying uniplate is useless. In fact, it's one of the most useful libraries I've ever used. It's simple and does sheer magic more often than not. However, for the sake of compositionality what (I think) one would like to do in this case is have two traversals: the outer which says "for every B, transform its A-children recursively like this" and the inner says "for every A, transform all of its children recursively, but until you see a B". You can't really do that with transform/rewrite in uniplate, so one has to fall back to descend which requires you to set up your recursion yourself. The documentation in Control.Lens.Plated alludes that the traversal above might just be possible using transformOnOff, but, unfortunately, it does not go into any detail how exactly could one achieve that. /Andrey On 09/02/2015 09:31 PM, mantkiew@gsd.uwaterloo.ca wrote:
+1 I've been missing such examples for a long time too.
Michał
Original Message From: Andrey Chudnov Sent: Wednesday, September 2, 2015 7:44 PM To: haskell-cafe Subject: [Haskell-cafe] Examples for Control.Lens.Plated?
Hello Cafe, I'm considering porting some of my code that uses uniplate to lens. But Control.Lens.Plated is giving me headaches. So I'm looking for remedy.
Has anyone used it and willing to share examples? I hope that seeing some of the combinators in action would help me understand the type signatures and documentation. What I'm particularly interested in is the following: 1) implementation of something like transformBi and rewriteBi using lens 2) usage of *On, *Off and *OnOff combinators (e.g., transformMOn, transformMOff, transformMOnOff). What I want to understand is the difference between the 3 variants. Also, what does it mean to "Transform every element in the tree in a region indicated by a supplied Traversal" and how exactly does the traversal define the region. 3) any recursive tree traversals/transformations using Plated that stop the recursion at a certain point (e.g., upon seeing a certain constructor)
I hope this isn't too vague, but, please, let me know if it is.
/Andrey _______________________________________________ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe
participants (2)
-
Andrey Chudnov
-
mantkiew@gsd.uwaterloo.ca