Re: First post: how to mimic a Java List with types?

2020-08-16 Thread Jack Park
Brandon,

Just a quick note to say that I conquered ConjunctiveList and have
DisjunctiveList coded.
After further tests to validate what it's doing, I'll post a gist to show
the working code.

You were entirely right: using definterface and defrecord, I can construct
these structures. Still a few tests to run.

Many thanks
Jack

On Sat, Aug 15, 2020 at 2:28 PM Brandon R  wrote:

> Hey Jack,
>
> Just been a fly on the wall for this convo, and aside from offering a
> specific solution, which others have done, I'm pretty certain this can be
> done with just protocols and records. Make a record (like your type) that
> implements the two protocols (like your interfaces). You could achieve your
> desired functionality without records and protocols but what you describe
> sounds like a fitting case for them.
>
> Members in such lists can be either other evaluable lists, or they can be
>> evaluable objects which perform computations
>>
>
> A simple Clojure list/vector can hold any type of data you put into it. So
> your record can hold a vector of these things, which can be represented as
> Clojure data structure (lists / maps / etc).
>
> You say you *need* to construct a type, but I urge you to challenge this
> assumption, again and again if needed. I think it's natural to think you
> need a type because of coming from Java/OOP land, especially if you were
> there a long time. Old patterns die hard?
>
> I could be wrong though. :)
>
>
> My 2 cents,
> Brandon
>
> On Sat, Aug 15, 2020 at 12:42 PM Jack Park 
> wrote:
>
>> Hi Erik,
>>
>> I think that teasing things apart helps along some dimensions, but the
>> problem I face, still thinking like a Java hacker, is that I need to put
>> things together:
>>
>> I need to construct a *type*  (deftype) which honors two different
>> interfaces, a list, and an evaluable object. I need the type because I want
>> to create it, then add members to the list, and then one of:
>> a) insert the object into another one (building and/or trees)
>> b) evaluate it - when it is the root of the tree.
>>
>> Members in such lists can be either other evaluable lists, or they can be
>> evaluable objects which perform computations - even with side effects - but
>> which return a boolean.
>>
>> The several ideas posted in this thread are greatly helping me to see
>> through this situation with fresh eyes, but, thus far, nothing has
>> convinced me to drop the goal of creating a type which is a list and
>> evaluable, into which I can insert conjunction or disjunction evaluators.
>>
>> Many thanks,
>> Jack
>>
>> On Sat, Aug 15, 2020 at 12:14 AM Erik Assum  wrote:
>>
>>> Why not tease things apart?
>>>
>>> (defn eval [x] ...)
>>>
>>> (some eval my-list) ;; or list
>>> (every? eval my-list) ;; and list
>>>
>>> https://clojuredocs.org/clojure.core/some
>>> https://clojuredocs.org/clojure.core/every_q
>>>
>>> Now, you can make the eval function polymorphic in several ways,
>>> simplest is to case or cond on some property of x. You could also use
>>> multimethods or a protocol to achieve this.
>>>
>>> https://insideclojure.org/2015/04/27/poly-perf/
>>>
>>> Erik.
>>> --
>>> i farta
>>>
>>> 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com <
>>> matthewdowne...@gmail.com>:
>>>
>>> 
>>>
>>> Another option would be to do what Alex is suggesting and define and as
>>> a function. Just because it’s a macro in clojure.core doesn’t mean you
>>> can’t write your own :)
>>>
>>> (defn eval' [x]
>>>   (if (map? x)
>>> (apply (:fn x) (:coll x))
>>> x))
>>>
>>> (defn and-list [& items]
>>>   (let [if? (fn [x] (if x true false))
>>> and' (fn [& args] (every? if? args))]
>>> {:fn and' :coll items}))
>>>
>>> (eval' true) ;=> true
>>> (eval' false) ;=> false
>>> (eval' (and-list 1 2 3)) ;=> true
>>> (eval' (and-list 1 2 3 false)) ;=> false
>>>
>>> Ditto with or.
>>> ​
>>> On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org
>>> wrote:
>>>
 Alex,

 I plan to explore this idea.
 Many thanks!

 Jack

 On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
 oleksand...@zalando.de> wrote:

> 
>
>
> Nevermind transducers: I've just realized that reduced can be used
> with the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>
> (defn andr
>   ([] true)
>   ([i] i)
>   ([r i] (let [o (and r i)]
>(if o
>  o
>  (reduced o)
>
> When it comes to the actual lists, it depends how you'd like to
> represent them.  E.g. I could imagine something like the following can be 
> a
> useful notation:
>
> [:and 1 2 [:or 3 4] 5]
>
> or even more direct:
>
> (quote (and 1 2 (or 3 4) 5))
>
> If you really want an interface-like look and feel, then protocols
> might be the right answer:
>
> (defprotocol Evaluable
>   (evaluate [this]))
>
> (defrecord AndList [items]
>   Evaluable
>   

Re: First post: how to mimic a Java List with types?

2020-08-15 Thread Jack Park
My first attempt at using records (showing my ignorance here) is found in
this gist
https://gist.github.com/KnowledgeGarden/0f6ce01ed9300d4f9bd0ee0c61e3d91b

It fails with this error (which doesn't give very good google)

Syntax error macroexpanding clojure.core/defn at (cljtest/core.clj:123:1).
>   - failed: vector? at: [:fn-tail :arity-1 :params] spec:
> :clojure.core.specs.alpha/param-list
>   - failed: (or (nil? %) (sequential? %)) at: [:fn-tail :arity-n :bodies]
> spec: :clojure.core.specs.alpha/params+body
>

I wonder what I am missing.
Thanks in advance for ideas.

-Jack

On Sat, Aug 15, 2020 at 4:18 PM Jack Park  wrote:

> Brandon!
>
> That just might be the idea I needed. Thank you.
>
> Film at 11...
>
> On Sat, Aug 15, 2020 at 2:28 PM Brandon R  wrote:
>
>> Hey Jack,
>>
>> Just been a fly on the wall for this convo, and aside from offering a
>> specific solution, which others have done, I'm pretty certain this can be
>> done with just protocols and records. Make a record (like your type) that
>> implements the two protocols (like your interfaces). You could achieve your
>> desired functionality without records and protocols but what you describe
>> sounds like a fitting case for them.
>>
>> Members in such lists can be either other evaluable lists, or they can be
>>> evaluable objects which perform computations
>>>
>>
>> A simple Clojure list/vector can hold any type of data you put into it.
>> So your record can hold a vector of these things, which can be represented
>> as Clojure data structure (lists / maps / etc).
>>
>> You say you *need* to construct a type, but I urge you to challenge this
>> assumption, again and again if needed. I think it's natural to think you
>> need a type because of coming from Java/OOP land, especially if you were
>> there a long time. Old patterns die hard?
>>
>> I could be wrong though. :)
>>
>>
>> My 2 cents,
>> Brandon
>>
>> On Sat, Aug 15, 2020 at 12:42 PM Jack Park 
>> wrote:
>>
>>> Hi Erik,
>>>
>>> I think that teasing things apart helps along some dimensions, but the
>>> problem I face, still thinking like a Java hacker, is that I need to put
>>> things together:
>>>
>>> I need to construct a *type*  (deftype) which honors two different
>>> interfaces, a list, and an evaluable object. I need the type because I want
>>> to create it, then add members to the list, and then one of:
>>> a) insert the object into another one (building and/or trees)
>>> b) evaluate it - when it is the root of the tree.
>>>
>>> Members in such lists can be either other evaluable lists, or they can
>>> be evaluable objects which perform computations - even with side effects -
>>> but which return a boolean.
>>>
>>> The several ideas posted in this thread are greatly helping me to see
>>> through this situation with fresh eyes, but, thus far, nothing has
>>> convinced me to drop the goal of creating a type which is a list and
>>> evaluable, into which I can insert conjunction or disjunction evaluators.
>>>
>>> Many thanks,
>>> Jack
>>>
>>> On Sat, Aug 15, 2020 at 12:14 AM Erik Assum  wrote:
>>>
 Why not tease things apart?

 (defn eval [x] ...)

 (some eval my-list) ;; or list
 (every? eval my-list) ;; and list

 https://clojuredocs.org/clojure.core/some
 https://clojuredocs.org/clojure.core/every_q

 Now, you can make the eval function polymorphic in several ways,
 simplest is to case or cond on some property of x. You could also use
 multimethods or a protocol to achieve this.

 https://insideclojure.org/2015/04/27/poly-perf/

 Erik.
 --
 i farta

 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com <
 matthewdowne...@gmail.com>:

 

 Another option would be to do what Alex is suggesting and define and
 as a function. Just because it’s a macro in clojure.core doesn’t mean you
 can’t write your own :)

 (defn eval' [x]
   (if (map? x)
 (apply (:fn x) (:coll x))
 x))

 (defn and-list [& items]
   (let [if? (fn [x] (if x true false))
 and' (fn [& args] (every? if? args))]
 {:fn and' :coll items}))

 (eval' true) ;=> true
 (eval' false) ;=> false
 (eval' (and-list 1 2 3)) ;=> true
 (eval' (and-list 1 2 3 false)) ;=> false

 Ditto with or.
 ​
 On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org
 wrote:

> Alex,
>
> I plan to explore this idea.
> Many thanks!
>
> Jack
>
> On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
> oleksand...@zalando.de> wrote:
>
>> 
>>
>>
>> Nevermind transducers: I've just realized that reduced can be used
>> with the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>>
>> (defn andr
>>   ([] true)
>>   ([i] i)
>>   ([r i] (let [o (and r i)]
>>(if o
>>  o
>>  (reduced o)
>>
>> 

Re: First post: how to mimic a Java List with types?

2020-08-15 Thread Jack Park
Brandon!

That just might be the idea I needed. Thank you.

Film at 11...

On Sat, Aug 15, 2020 at 2:28 PM Brandon R  wrote:

> Hey Jack,
>
> Just been a fly on the wall for this convo, and aside from offering a
> specific solution, which others have done, I'm pretty certain this can be
> done with just protocols and records. Make a record (like your type) that
> implements the two protocols (like your interfaces). You could achieve your
> desired functionality without records and protocols but what you describe
> sounds like a fitting case for them.
>
> Members in such lists can be either other evaluable lists, or they can be
>> evaluable objects which perform computations
>>
>
> A simple Clojure list/vector can hold any type of data you put into it. So
> your record can hold a vector of these things, which can be represented as
> Clojure data structure (lists / maps / etc).
>
> You say you *need* to construct a type, but I urge you to challenge this
> assumption, again and again if needed. I think it's natural to think you
> need a type because of coming from Java/OOP land, especially if you were
> there a long time. Old patterns die hard?
>
> I could be wrong though. :)
>
>
> My 2 cents,
> Brandon
>
> On Sat, Aug 15, 2020 at 12:42 PM Jack Park 
> wrote:
>
>> Hi Erik,
>>
>> I think that teasing things apart helps along some dimensions, but the
>> problem I face, still thinking like a Java hacker, is that I need to put
>> things together:
>>
>> I need to construct a *type*  (deftype) which honors two different
>> interfaces, a list, and an evaluable object. I need the type because I want
>> to create it, then add members to the list, and then one of:
>> a) insert the object into another one (building and/or trees)
>> b) evaluate it - when it is the root of the tree.
>>
>> Members in such lists can be either other evaluable lists, or they can be
>> evaluable objects which perform computations - even with side effects - but
>> which return a boolean.
>>
>> The several ideas posted in this thread are greatly helping me to see
>> through this situation with fresh eyes, but, thus far, nothing has
>> convinced me to drop the goal of creating a type which is a list and
>> evaluable, into which I can insert conjunction or disjunction evaluators.
>>
>> Many thanks,
>> Jack
>>
>> On Sat, Aug 15, 2020 at 12:14 AM Erik Assum  wrote:
>>
>>> Why not tease things apart?
>>>
>>> (defn eval [x] ...)
>>>
>>> (some eval my-list) ;; or list
>>> (every? eval my-list) ;; and list
>>>
>>> https://clojuredocs.org/clojure.core/some
>>> https://clojuredocs.org/clojure.core/every_q
>>>
>>> Now, you can make the eval function polymorphic in several ways,
>>> simplest is to case or cond on some property of x. You could also use
>>> multimethods or a protocol to achieve this.
>>>
>>> https://insideclojure.org/2015/04/27/poly-perf/
>>>
>>> Erik.
>>> --
>>> i farta
>>>
>>> 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com <
>>> matthewdowne...@gmail.com>:
>>>
>>> 
>>>
>>> Another option would be to do what Alex is suggesting and define and as
>>> a function. Just because it’s a macro in clojure.core doesn’t mean you
>>> can’t write your own :)
>>>
>>> (defn eval' [x]
>>>   (if (map? x)
>>> (apply (:fn x) (:coll x))
>>> x))
>>>
>>> (defn and-list [& items]
>>>   (let [if? (fn [x] (if x true false))
>>> and' (fn [& args] (every? if? args))]
>>> {:fn and' :coll items}))
>>>
>>> (eval' true) ;=> true
>>> (eval' false) ;=> false
>>> (eval' (and-list 1 2 3)) ;=> true
>>> (eval' (and-list 1 2 3 false)) ;=> false
>>>
>>> Ditto with or.
>>> ​
>>> On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org
>>> wrote:
>>>
 Alex,

 I plan to explore this idea.
 Many thanks!

 Jack

 On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
 oleksand...@zalando.de> wrote:

> 
>
>
> Nevermind transducers: I've just realized that reduced can be used
> with the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>
> (defn andr
>   ([] true)
>   ([i] i)
>   ([r i] (let [o (and r i)]
>(if o
>  o
>  (reduced o)
>
> When it comes to the actual lists, it depends how you'd like to
> represent them.  E.g. I could imagine something like the following can be 
> a
> useful notation:
>
> [:and 1 2 [:or 3 4] 5]
>
> or even more direct:
>
> (quote (and 1 2 (or 3 4) 5))
>
> If you really want an interface-like look and feel, then protocols
> might be the right answer:
>
> (defprotocol Evaluable
>   (evaluate [this]))
>
> (defrecord AndList [items]
>   Evaluable
>   (evaluate [this]
> (reduce andr (:items this
>
> user> (evaluate (->AndList [1 2 3]))
> 3
> user> (evaluate (->AndList [1 false 3]))
> false
>
> To complete it, you'll need to add the OrList and sneak (map evaluate)

Re: First post: how to mimic a Java List with types?

2020-08-15 Thread Brandon R
Hey Jack,

Just been a fly on the wall for this convo, and aside from offering a
specific solution, which others have done, I'm pretty certain this can be
done with just protocols and records. Make a record (like your type) that
implements the two protocols (like your interfaces). You could achieve your
desired functionality without records and protocols but what you describe
sounds like a fitting case for them.

Members in such lists can be either other evaluable lists, or they can be
> evaluable objects which perform computations
>

A simple Clojure list/vector can hold any type of data you put into it. So
your record can hold a vector of these things, which can be represented as
Clojure data structure (lists / maps / etc).

You say you *need* to construct a type, but I urge you to challenge this
assumption, again and again if needed. I think it's natural to think you
need a type because of coming from Java/OOP land, especially if you were
there a long time. Old patterns die hard?

I could be wrong though. :)


My 2 cents,
Brandon

On Sat, Aug 15, 2020 at 12:42 PM Jack Park  wrote:

> Hi Erik,
>
> I think that teasing things apart helps along some dimensions, but the
> problem I face, still thinking like a Java hacker, is that I need to put
> things together:
>
> I need to construct a *type*  (deftype) which honors two different
> interfaces, a list, and an evaluable object. I need the type because I want
> to create it, then add members to the list, and then one of:
> a) insert the object into another one (building and/or trees)
> b) evaluate it - when it is the root of the tree.
>
> Members in such lists can be either other evaluable lists, or they can be
> evaluable objects which perform computations - even with side effects - but
> which return a boolean.
>
> The several ideas posted in this thread are greatly helping me to see
> through this situation with fresh eyes, but, thus far, nothing has
> convinced me to drop the goal of creating a type which is a list and
> evaluable, into which I can insert conjunction or disjunction evaluators.
>
> Many thanks,
> Jack
>
> On Sat, Aug 15, 2020 at 12:14 AM Erik Assum  wrote:
>
>> Why not tease things apart?
>>
>> (defn eval [x] ...)
>>
>> (some eval my-list) ;; or list
>> (every? eval my-list) ;; and list
>>
>> https://clojuredocs.org/clojure.core/some
>> https://clojuredocs.org/clojure.core/every_q
>>
>> Now, you can make the eval function polymorphic in several ways, simplest
>> is to case or cond on some property of x. You could also use multimethods
>> or a protocol to achieve this.
>>
>> https://insideclojure.org/2015/04/27/poly-perf/
>>
>> Erik.
>> --
>> i farta
>>
>> 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com <
>> matthewdowne...@gmail.com>:
>>
>> 
>>
>> Another option would be to do what Alex is suggesting and define and as
>> a function. Just because it’s a macro in clojure.core doesn’t mean you
>> can’t write your own :)
>>
>> (defn eval' [x]
>>   (if (map? x)
>> (apply (:fn x) (:coll x))
>> x))
>>
>> (defn and-list [& items]
>>   (let [if? (fn [x] (if x true false))
>> and' (fn [& args] (every? if? args))]
>> {:fn and' :coll items}))
>>
>> (eval' true) ;=> true
>> (eval' false) ;=> false
>> (eval' (and-list 1 2 3)) ;=> true
>> (eval' (and-list 1 2 3 false)) ;=> false
>>
>> Ditto with or.
>> ​
>> On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org
>> wrote:
>>
>>> Alex,
>>>
>>> I plan to explore this idea.
>>> Many thanks!
>>>
>>> Jack
>>>
>>> On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
>>> oleksand...@zalando.de> wrote:
>>>
 


 Nevermind transducers: I've just realized that reduced can be used with
 the normal reduce.  E.g. here's short-circuiting AND-reduction fn:

 (defn andr
   ([] true)
   ([i] i)
   ([r i] (let [o (and r i)]
(if o
  o
  (reduced o)

 When it comes to the actual lists, it depends how you'd like to
 represent them.  E.g. I could imagine something like the following can be a
 useful notation:

 [:and 1 2 [:or 3 4] 5]

 or even more direct:

 (quote (and 1 2 (or 3 4) 5))

 If you really want an interface-like look and feel, then protocols
 might be the right answer:

 (defprotocol Evaluable
   (evaluate [this]))

 (defrecord AndList [items]
   Evaluable
   (evaluate [this]
 (reduce andr (:items this

 user> (evaluate (->AndList [1 2 3]))
 3
 user> (evaluate (->AndList [1 false 3]))
 false

 To complete it, you'll need to add the OrList and sneak (map evaluate)
 in the reduce call in both And- and OrList.

 Cheers,
 --
 Alex

>>> 

>>> --
>> You received this message because you are subscribed to the Google
>> Groups "Clojure" group.
>> To post to this group, send email to clojure@googlegroups.com
>> Note that posts from new members are 

Re: First post: how to mimic a Java List with types?

2020-08-15 Thread Jack Park
Hi Erik,

I think that teasing things apart helps along some dimensions, but the
problem I face, still thinking like a Java hacker, is that I need to put
things together:

I need to construct a *type*  (deftype) which honors two different
interfaces, a list, and an evaluable object. I need the type because I want
to create it, then add members to the list, and then one of:
a) insert the object into another one (building and/or trees)
b) evaluate it - when it is the root of the tree.

Members in such lists can be either other evaluable lists, or they can be
evaluable objects which perform computations - even with side effects - but
which return a boolean.

The several ideas posted in this thread are greatly helping me to see
through this situation with fresh eyes, but, thus far, nothing has
convinced me to drop the goal of creating a type which is a list and
evaluable, into which I can insert conjunction or disjunction evaluators.

Many thanks,
Jack

On Sat, Aug 15, 2020 at 12:14 AM Erik Assum  wrote:

> Why not tease things apart?
>
> (defn eval [x] ...)
>
> (some eval my-list) ;; or list
> (every? eval my-list) ;; and list
>
> https://clojuredocs.org/clojure.core/some
> https://clojuredocs.org/clojure.core/every_q
>
> Now, you can make the eval function polymorphic in several ways, simplest
> is to case or cond on some property of x. You could also use multimethods
> or a protocol to achieve this.
>
> https://insideclojure.org/2015/04/27/poly-perf/
>
> Erik.
> --
> i farta
>
> 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com <
> matthewdowne...@gmail.com>:
>
> 
>
> Another option would be to do what Alex is suggesting and define and as a
> function. Just because it’s a macro in clojure.core doesn’t mean you can’t
> write your own :)
>
> (defn eval' [x]
>   (if (map? x)
> (apply (:fn x) (:coll x))
> x))
>
> (defn and-list [& items]
>   (let [if? (fn [x] (if x true false))
> and' (fn [& args] (every? if? args))]
> {:fn and' :coll items}))
>
> (eval' true) ;=> true
> (eval' false) ;=> false
> (eval' (and-list 1 2 3)) ;=> true
> (eval' (and-list 1 2 3 false)) ;=> false
>
> Ditto with or.
> ​
> On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org
> wrote:
>
>> Alex,
>>
>> I plan to explore this idea.
>> Many thanks!
>>
>> Jack
>>
>> On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin 
>> wrote:
>>
>>> 
>>>
>>>
>>> Nevermind transducers: I've just realized that reduced can be used with
>>> the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>>>
>>> (defn andr
>>>   ([] true)
>>>   ([i] i)
>>>   ([r i] (let [o (and r i)]
>>>(if o
>>>  o
>>>  (reduced o)
>>>
>>> When it comes to the actual lists, it depends how you'd like to
>>> represent them.  E.g. I could imagine something like the following can be a
>>> useful notation:
>>>
>>> [:and 1 2 [:or 3 4] 5]
>>>
>>> or even more direct:
>>>
>>> (quote (and 1 2 (or 3 4) 5))
>>>
>>> If you really want an interface-like look and feel, then protocols might
>>> be the right answer:
>>>
>>> (defprotocol Evaluable
>>>   (evaluate [this]))
>>>
>>> (defrecord AndList [items]
>>>   Evaluable
>>>   (evaluate [this]
>>> (reduce andr (:items this
>>>
>>> user> (evaluate (->AndList [1 2 3]))
>>> 3
>>> user> (evaluate (->AndList [1 false 3]))
>>> false
>>>
>>> To complete it, you'll need to add the OrList and sneak (map evaluate)
>>> in the reduce call in both And- and OrList.
>>>
>>> Cheers,
>>> --
>>> Alex
>>>
>> 
>>>
>> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/clojure/cfac729f-b8e4-4f95-94b0-78345d10f457n%40googlegroups.com
> 
> .
>
> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To 

Re: First post: how to mimic a Java List with types?

2020-08-15 Thread Erik Assum
Why not tease things apart?

(defn eval [x] ...)

(some eval my-list) ;; or list
(every? eval my-list) ;; and list

https://clojuredocs.org/clojure.core/some
https://clojuredocs.org/clojure.core/every_q

Now, you can make the eval function polymorphic in several ways, simplest is to 
case or cond on some property of x. You could also use multimethods or a 
protocol to achieve this. 

https://insideclojure.org/2015/04/27/poly-perf/

Erik. 
-- 
i farta

> 15. aug. 2020 kl. 02:04 skrev matthew...@gmail.com 
> :
> 
> 
> Another option would be to do what Alex is suggesting and define and as a 
> function. Just because it’s a macro in clojure.core doesn’t mean you can’t 
> write your own :)
> 
> (defn eval' [x]
>   (if (map? x)
> (apply (:fn x) (:coll x))
> x))
> 
> (defn and-list [& items]
>   (let [if? (fn [x] (if x true false))
> and' (fn [& args] (every? if? args))]
> {:fn and' :coll items}))
> 
> (eval' true) ;=> true
> (eval' false) ;=> false
> (eval' (and-list 1 2 3)) ;=> true
> (eval' (and-list 1 2 3 false)) ;=> false
> Ditto with or.
> 
>> On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org wrote:
>> Alex,
>> 
>> I plan to explore this idea.
>> Many thanks!
>> 
>> Jack
>> 
>>> On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin  
>>> wrote:
>>> 
>>> 
>> 
>>> 
>>> Nevermind transducers: I've just realized that reduced can be used with the 
>>> normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>>> 
>>> (defn andr
>>>   ([] true)
>>>   ([i] i)
>>>   ([r i] (let [o (and r i)]
>>>(if o
>>>  o
>>>  (reduced o)
>>> 
>>> When it comes to the actual lists, it depends how you'd like to represent 
>>> them.  E.g. I could imagine something like the following can be a useful 
>>> notation:
>>> 
>>> [:and 1 2 [:or 3 4] 5]
>>> 
>>> or even more direct:
>>> 
>>> (quote (and 1 2 (or 3 4) 5))
>>> 
>>> If you really want an interface-like look and feel, then protocols might be 
>>> the right answer:
>>> 
>>> (defprotocol Evaluable
>>>   (evaluate [this]))
>>> 
>>> (defrecord AndList [items]
>>>   Evaluable
>>>   (evaluate [this]
>>> (reduce andr (:items this
>>> 
>>> user> (evaluate (->AndList [1 2 3]))
>>> 3
>>> user> (evaluate (->AndList [1 false 3]))
>>> false
>>> 
>>> To complete it, you'll need to add the OrList and sneak (map evaluate) in 
>>> the reduce call in both And- and OrList.
>>> 
>>> Cheers,
>>> --
>>> Alex
>> 
>>> 
> 
> -- 
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with your 
> first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> --- 
> You received this message because you are subscribed to the Google Groups 
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an 
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit 
> https://groups.google.com/d/msgid/clojure/cfac729f-b8e4-4f95-94b0-78345d10f457n%40googlegroups.com.

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/5B42B3BC-E20D-446E-82EF-0D1BFC36DA5F%40assum.net.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread matthew...@gmail.com


Another option would be to do what Alex is suggesting and define and as a 
function. Just because it’s a macro in clojure.core doesn’t mean you can’t 
write your own :)

(defn eval' [x]
  (if (map? x)
(apply (:fn x) (:coll x))
x))

(defn and-list [& items]
  (let [if? (fn [x] (if x true false))
and' (fn [& args] (every? if? args))]
{:fn and' :coll items}))

(eval' true) ;=> true
(eval' false) ;=> false
(eval' (and-list 1 2 3)) ;=> true
(eval' (and-list 1 2 3 false)) ;=> false

Ditto with or. 
On Friday, August 14, 2020 at 4:27:19 PM UTC-5 jack...@topicquests.org 
wrote:

> Alex,
>
> I plan to explore this idea.
> Many thanks!
>
> Jack
>
> On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin  
> wrote:
>
>> 
>>
>>
>> Nevermind transducers: I've just realized that reduced can be used with 
>> the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>>
>> (defn andr
>>   ([] true)
>>   ([i] i)
>>   ([r i] (let [o (and r i)]
>>(if o
>>  o
>>  (reduced o)
>>
>> When it comes to the actual lists, it depends how you'd like to represent 
>> them.  E.g. I could imagine something like the following can be a useful 
>> notation:
>>
>> [:and 1 2 [:or 3 4] 5]
>>
>> or even more direct:
>>
>> (quote (and 1 2 (or 3 4) 5))
>>
>> If you really want an interface-like look and feel, then protocols might 
>> be the right answer:
>>
>> (defprotocol Evaluable
>>   (evaluate [this]))
>>
>> (defrecord AndList [items]
>>   Evaluable
>>   (evaluate [this]
>> (reduce andr (:items this
>>
>> user> (evaluate (->AndList [1 2 3]))
>> 3
>> user> (evaluate (->AndList [1 false 3]))
>> false
>>
>> To complete it, you'll need to add the OrList and sneak (map evaluate) in 
>> the reduce call in both And- and OrList.
>>
>> Cheers,
>> --
>> Alex
>>
> 
>>
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/cfac729f-b8e4-4f95-94b0-78345d10f457n%40googlegroups.com.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Jack Park
Alex,

I plan to explore this idea.
Many thanks!

Jack

On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
oleksandr.shul...@zalando.de> wrote:

> 
>
>
> Nevermind transducers: I've just realized that reduced can be used with
> the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>
> (defn andr
>   ([] true)
>   ([i] i)
>   ([r i] (let [o (and r i)]
>(if o
>  o
>  (reduced o)
>
> When it comes to the actual lists, it depends how you'd like to represent
> them.  E.g. I could imagine something like the following can be a useful
> notation:
>
> [:and 1 2 [:or 3 4] 5]
>
> or even more direct:
>
> (quote (and 1 2 (or 3 4) 5))
>
> If you really want an interface-like look and feel, then protocols might
> be the right answer:
>
> (defprotocol Evaluable
>   (evaluate [this]))
>
> (defrecord AndList [items]
>   Evaluable
>   (evaluate [this]
> (reduce andr (:items this
>
> user> (evaluate (->AndList [1 2 3]))
> 3
> user> (evaluate (->AndList [1 false 3]))
> false
>
> To complete it, you'll need to add the OrList and sneak (map evaluate) in
> the reduce call in both And- and OrList.
>
> Cheers,
> --
> Alex
> 
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CAH6s0fwVA5zhAJVdUaEMZN%2BhzThM8XMU1VtEWcej3PogPmxoLg%40mail.gmail.com.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Jack Park
Wow!

I say that because that might be getting closer to what I have in mind but
still not there yet.
I'm really trying to develop a type which honors two interfaces, one for
the list object, and one for the IEvaluable object.

As a type, I invoke it, then add objects to it, then place it, as an
IEvaluable object inside another such collection. Perhaps it is the first -
root - which begins an and/or network of IEvaluable objects, some of which
are the workers which go outside and make computations before returning
their boolean.

But, I have been wandering down another rabbit hole, the one where I ignore
list comprehensions and proxy an ArrayList.

I have code which almost runs, but which is far from perfect.
I created a gist which exposes my current experiment - which is close, but
no cigars yet.

https://gist.github.com/KnowledgeGarden/004fd93a78e2238c878b585f158759f9

Thanks
Jack

On Fri, Aug 14, 2020 at 1:38 PM Oleksandr Shulgin <
oleksandr.shul...@zalando.de> wrote:

> On Fri, Aug 14, 2020 at 8:44 PM Jack Park 
> wrote:
>
>> This idea shows up early in Clojure text books. This concept comes to
>> mind rather quickly:
>>
>> (def and_list (ArrayList.)
>>...
>> )
>>
>> But, in the end it is an ArrayList which has an interface-defined
>> behavior, e.g. boolean eval(); (from Java)
>> Thus far, in a tiny VSCode project, I defined
>>
>> (definterface IEvaluable
>>(^boolean runIt []))
>>
>> and defined a simple object which will return false and one which will
>> return true. I'll use those to populate a conjunctive and a disjunctive
>> list.
>>
>> Now I must define a list object which runs that interface.
>>
>> Still digging and experimenting, but, on the surface, this approach
>> appears to be possible.
>>
>> From above, as a sketch:
>>
>> (def and_list (ArrayList.)
>>   IEvaluable
>>   (runIt [this]
>>   ))
>> )
>>
>> Meanwhile, I found this https://clojuredocs.org/clojure.core/proxy-super
>> which is now on the table to explore.
>>
>
> Nevermind transducers: I've just realized that reduced can be used with
> the normal reduce.  E.g. here's short-circuiting AND-reduction fn:
>
> (defn andr
>   ([] true)
>   ([i] i)
>   ([r i] (let [o (and r i)]
>(if o
>  o
>  (reduced o)
>
> When it comes to the actual lists, it depends how you'd like to represent
> them.  E.g. I could imagine something like the following can be a useful
> notation:
>
> [:and 1 2 [:or 3 4] 5]
>
> or even more direct:
>
> (quote (and 1 2 (or 3 4) 5))
>
> If you really want an interface-like look and feel, then protocols might
> be the right answer:
>
> (defprotocol Evaluable
>   (evaluate [this]))
>
> (defrecord AndList [items]
>   Evaluable
>   (evaluate [this]
> (reduce andr (:items this
>
> user> (evaluate (->AndList [1 2 3]))
> 3
> user> (evaluate (->AndList [1 false 3]))
> false
>
> To complete it, you'll need to add the OrList and sneak (map evaluate) in
> the reduce call in both And- and OrList.
>
> Cheers,
> --
> Alex
>
> On Fri, Aug 14, 2020 at 3:41 AM Jesús Gómez  wrote:
>>
>>> Why not to Java-Interop with that Interface and those Classes directly,
>>> the same way you use them in Java?
>>>
>>> El jue., 13 ago. 2020 a las 22:54, Jack Park ()
>>> escribió:
>>>
 The problem:

 In Java, I have an interface *IInferrable* which is basically  boolean
 eval();

 Any Java object which extends IInferrable, no matter what it is, will
 answer to eval() and return a boolean.
 The idea lies at the heart of an inference engine.

 But, I also define a class *AndList* which implements IInferrable and
 extends java.util.ArrayList

 So, AndList, and its sibling OrList behave just like a List object, but
 also will answer to eval() by running the collection and dealing with what
 each element returns when it, too, is eval()'d.

 I'd really love to discover how to pull that off in Clojure.

 Many thanks in advance. -Jack

>>> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/clojure/CACACo5Rj3U1CJdEy431j7EBpR4oOVccKoGtLjCRPdiKd%3DvgLTQ%40mail.gmail.com
> 
> .
>

-- 
You received this message because 

Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Oleksandr Shulgin
On Fri, Aug 14, 2020 at 8:44 PM Jack Park  wrote:

> This idea shows up early in Clojure text books. This concept comes to mind
> rather quickly:
>
> (def and_list (ArrayList.)
>...
> )
>
> But, in the end it is an ArrayList which has an interface-defined
> behavior, e.g. boolean eval(); (from Java)
> Thus far, in a tiny VSCode project, I defined
>
> (definterface IEvaluable
>(^boolean runIt []))
>
> and defined a simple object which will return false and one which will
> return true. I'll use those to populate a conjunctive and a disjunctive
> list.
>
> Now I must define a list object which runs that interface.
>
> Still digging and experimenting, but, on the surface, this approach
> appears to be possible.
>
> From above, as a sketch:
>
> (def and_list (ArrayList.)
>   IEvaluable
>   (runIt [this]
>   ))
> )
>
> Meanwhile, I found this https://clojuredocs.org/clojure.core/proxy-super
> which is now on the table to explore.
>

Nevermind transducers: I've just realized that reduced can be used with the
normal reduce.  E.g. here's short-circuiting AND-reduction fn:

(defn andr
  ([] true)
  ([i] i)
  ([r i] (let [o (and r i)]
   (if o
 o
 (reduced o)

When it comes to the actual lists, it depends how you'd like to represent
them.  E.g. I could imagine something like the following can be a useful
notation:

[:and 1 2 [:or 3 4] 5]

or even more direct:

(quote (and 1 2 (or 3 4) 5))

If you really want an interface-like look and feel, then protocols might be
the right answer:

(defprotocol Evaluable
  (evaluate [this]))

(defrecord AndList [items]
  Evaluable
  (evaluate [this]
(reduce andr (:items this

user> (evaluate (->AndList [1 2 3]))
3
user> (evaluate (->AndList [1 false 3]))
false

To complete it, you'll need to add the OrList and sneak (map evaluate) in
the reduce call in both And- and OrList.

Cheers,
--
Alex

On Fri, Aug 14, 2020 at 3:41 AM Jesús Gómez  wrote:
>
>> Why not to Java-Interop with that Interface and those Classes directly,
>> the same way you use them in Java?
>>
>> El jue., 13 ago. 2020 a las 22:54, Jack Park ()
>> escribió:
>>
>>> The problem:
>>>
>>> In Java, I have an interface *IInferrable* which is basically  boolean
>>> eval();
>>>
>>> Any Java object which extends IInferrable, no matter what it is, will
>>> answer to eval() and return a boolean.
>>> The idea lies at the heart of an inference engine.
>>>
>>> But, I also define a class *AndList* which implements IInferrable and
>>> extends java.util.ArrayList
>>>
>>> So, AndList, and its sibling OrList behave just like a List object, but
>>> also will answer to eval() by running the collection and dealing with what
>>> each element returns when it, too, is eval()'d.
>>>
>>> I'd really love to discover how to pull that off in Clojure.
>>>
>>> Many thanks in advance. -Jack
>>>
>>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CACACo5Rj3U1CJdEy431j7EBpR4oOVccKoGtLjCRPdiKd%3DvgLTQ%40mail.gmail.com.


RE: First post: how to mimic a Java List with types?

2020-08-14 Thread Sam Hahn
Jack - I'll call you :)  Cheers - Sam


 Original Message 
Subject: Re: First post: how to mimic a Java List with types?
From: Jack Park 
Date: Fri, August 14, 2020 11:34 am
To: clojure@googlegroups.com

Mapping and transducers seems appropriate, though I'm still wrapping my head around how to make this work.From the "class with functions" mindset, I need an ArrayList into which I can:a) add members to the list from time to timeb) run eval() on it; a conjunctive list will exit false on first false firing of any member, or default exit true otherwise; a disjunctive list will exit true on first true firing of a member, and default false.When I read the code here, I am not yet clear (sorry, it's  on me, not the code) how to make such a "class-like" object.I am still exploring this avenue, as well as looking at java-interop or something about a proxy.Many thanks.JackOn Fri, Aug 14, 2020 at 1:25 AM Oleksandr Shulgin  wrote:On Fri, Aug 14, 2020 at 9:05 AM Oleksandr Shulgin  wrote:On Fri, Aug 14, 2020 at 7:51 AM Alexandre Almosni  wrote:Maybe your objects could be defined by a map containing functions and objects.So exampleAndList = {:fn and, :coll [a b c]}And then eval goes through your objects recursively, using(def eval [o](apply (:fn o) (map eval (:coll o - with a special case that if o is not a map but say a Boolean you just return itselfA slight problem with that approach is that clojure.core/and is not a function, but a macro: the reason being is that it stops evaluating forms as soon as it hits a falsey value (similar for "or").A smart implementation of And/OrList would like to short-circuit as well I guess, so you'll need to express that somehow.Of the clojure.core library that property is satisfied by transducers: https://clojure.org/reference/transducers#_early_terminationI came up with the following:;; and-transducer with early termination: (defn xand [rf]   (fn     ([] (rf))     ([res] (rf res))     ([res inp] (if inp                  (rf res inp)                  (reduced inp);; reducing function implementing and:  (defn andr   ([] true)   ([i] i)   ([r i] (and r i)));; noisy variant of get: (defn noisy-get  ([k]   (fn [m]     (noisy-get m k)))  ([m k]   (println "noisy-get" m k)   (get m k)));; all in action:user> (def xf (comp (map (noisy-get :data))                    xand))#'user/xfuser> (transduce xf andr [{:data 1} {:data false} {:no-data 3}])noisy-get {:data 1} :datanoisy-get {:data false} :datafalseuser> (transduce xf andr [{:data 1} {:data 2} {:no-data 3} {:data 4}])noisy-get {:data 1} :datanoisy-get {:data 2} :datanoisy-get {:no-data 3} :dataniluser> (transduce xf andr [{:data 1} {:data 2} {:data 3} {:data 4}])noisy-get {:data 1} :datanoisy-get {:data 2} :datanoisy-get {:data 3} :datanoisy-get {:data 4} :data4It does feel a bit redundant to have the reducing function on top of a transducer that accomplishes mostly the same, but I haven't found a way to make it shorter.Cheers,--AlexOn 14 Aug 2020, at 02:24, Jack Park  wrote:The problem:In Java, I have an interface IInferrable which is basically  boolean eval();Any Java object which extends IInferrable, no matter what it is, will answer to eval() and return a boolean.The idea lies at the heart of an inference engine.But, I also define a class AndList which implements IInferrable and extends java.util.ArrayListSo, AndList, and its sibling OrList behave just like a List object, but also will answer to eval() by running the collection and dealing with what each element returns when it, too, is eval()'d.I'd really love to discover how to pull that off in Clojure.   --  You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en ---  You received this message because you are subscribed to the Google Groups "Clojure" group. To unsubscribe from this group and stop receiving emails from it, send an email to clojure+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/clojure/CACACo5TDpMg_CEhE2ytwZv9R1L3%3DifayFLYTs6KC80vON59hiw%40mail.gmail.com.   --  You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en ---  You received this message because you 

Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Jack Park
This idea shows up early in Clojure text books. This concept comes to mind
rather quickly:

(def and_list (ArrayList.)
   ...
)

But, in the end it is an ArrayList which has an interface-defined behavior,
e.g. boolean eval(); (from Java)
Thus far, in a tiny VSCode project, I defined

(definterface IEvaluable
   (^boolean runIt []))

and defined a simple object which will return false and one which will
return true. I'll use those to populate a conjunctive and a disjunctive
list.

Now I must define a list object which runs that interface.

Still digging and experimenting, but, on the surface, this approach appears
to be possible.

>From above, as a sketch:

(def and_list (ArrayList.)
  IEvaluable
  (runIt [this]
  ))
)

Meanwhile, I found this https://clojuredocs.org/clojure.core/proxy-super
which is now on the table to explore.

Many thanks
Jack

On Fri, Aug 14, 2020 at 3:41 AM Jesús Gómez  wrote:

> Why not to Java-Interop with that Interface and those Classes directly,
> the same way you use them in Java?
>
> El jue., 13 ago. 2020 a las 22:54, Jack Park ()
> escribió:
>
>> The problem:
>>
>> In Java, I have an interface *IInferrable* which is basically  boolean
>> eval();
>>
>> Any Java object which extends IInferrable, no matter what it is, will
>> answer to eval() and return a boolean.
>> The idea lies at the heart of an inference engine.
>>
>> But, I also define a class *AndList* which implements IInferrable and
>> extends java.util.ArrayList
>>
>> So, AndList, and its sibling OrList behave just like a List object, but
>> also will answer to eval() by running the collection and dealing with what
>> each element returns when it, too, is eval()'d.
>>
>> I'd really love to discover how to pull that off in Clojure.
>>
>> Many thanks in advance. -Jack
>>
>> --
>> You received this message because you are subscribed to the Google
>> Groups "Clojure" group.
>> To post to this group, send email to clojure@googlegroups.com
>> Note that posts from new members are moderated - please be patient with
>> your first post.
>> To unsubscribe from this group, send email to
>> clojure+unsubscr...@googlegroups.com
>> For more options, visit this group at
>> http://groups.google.com/group/clojure?hl=en
>> ---
>> You received this message because you are subscribed to the Google Groups
>> "Clojure" group.
>> To unsubscribe from this group and stop receiving emails from it, send an
>> email to clojure+unsubscr...@googlegroups.com.
>> To view this discussion on the web visit
>> https://groups.google.com/d/msgid/clojure/3e2ffc86-0e4f-4c0c-92c3-58e0848d5ba7o%40googlegroups.com
>> 
>> .
>>
> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/clojure/CAO9z-97N15E_17FRkDN_gbneXfkMkrS615RV5UwGMf3%2Bos%3DSLQ%40mail.gmail.com
> 
> .
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CAH6s0fxiGQiZ4gUgEs42ScKWmxhQDtEd_N8bfgcbr2TObu7gww%40mail.gmail.com.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Jack Park
Mapping and transducers seems appropriate, though I'm still wrapping my
head around how to make this work.
>From the "class with functions" mindset, I need an ArrayList into which I
can:
a) add members to the list from time to time
b) run eval() on it; a conjunctive list will exit false on first false
firing of any member, or default exit true otherwise; a disjunctive list
will exit true on first true firing of a member, and default false.

When I read the code here, I am not yet clear (sorry, it's  on me, not the
code) how to make such a "class-like" object.

I am still exploring this avenue, as well as looking at java-interop or
something about a proxy.

Many thanks.
Jack

On Fri, Aug 14, 2020 at 1:25 AM Oleksandr Shulgin <
oleksandr.shul...@zalando.de> wrote:

> On Fri, Aug 14, 2020 at 9:05 AM Oleksandr Shulgin <
> oleksandr.shul...@zalando.de> wrote:
>
>> On Fri, Aug 14, 2020 at 7:51 AM Alexandre Almosni <
>> alexandre.almo...@gmail.com> wrote:
>>
>>> Maybe your objects could be defined by a map containing functions and
>>> objects.
>>>
>>> So exampleAndList = {:fn and, :coll [a b c]}
>>>
>>>
>>> And then eval goes through your objects recursively, using
>>>
>>> (def eval [o]
>>> (apply (:fn o) (map eval (:coll o
>>>
>>> - with a special case that if o is not a map but say a Boolean you just
>>> return itself
>>>
>>
>> A slight problem with that approach is that clojure.core/and is not a
>> function, but a macro: the reason being is that it stops evaluating forms
>> as soon as it hits a falsey value (similar for "or").
>> A smart implementation of And/OrList would like to short-circuit as well
>> I guess, so you'll need to express that somehow.
>>
>> Of the clojure.core library that property is satisfied by transducers:
>> https://clojure.org/reference/transducers#_early_termination
>>
>
> I came up with the following:
>
> ;; and-transducer with early termination:
>  (defn xand [rf]
>(fn
>  ([] (rf))
>  ([res] (rf res))
>  ([res inp] (if inp
>   (rf res inp)
>   (reduced inp)
>
> ;; reducing function implementing and:
>   (defn andr
>([] true)
>([i] i)
>([r i] (and r i)))
>
> ;; noisy variant of get:
>  (defn noisy-get
>   ([k]
>(fn [m]
>  (noisy-get m k)))
>   ([m k]
>(println "noisy-get" m k)
>(get m k)))
>
> ;; all in action:
> user> (def xf (comp (map (noisy-get :data))
> xand))
> #'user/xf
> user> (transduce xf andr [{:data 1} {:data false} {:no-data 3}])
> noisy-get {:data 1} :data
> noisy-get {:data false} :data
> false
> user> (transduce xf andr [{:data 1} {:data 2} {:no-data 3} {:data 4}])
> noisy-get {:data 1} :data
> noisy-get {:data 2} :data
> noisy-get {:no-data 3} :data
> nil
> user> (transduce xf andr [{:data 1} {:data 2} {:data 3} {:data 4}])
> noisy-get {:data 1} :data
> noisy-get {:data 2} :data
> noisy-get {:data 3} :data
> noisy-get {:data 4} :data
> 4
>
> It does feel a bit redundant to have the reducing function on top of a
> transducer that accomplishes mostly the same, but I haven't found a way to
> make it shorter.
>
> Cheers,
> --
> Alex
>
>> On 14 Aug 2020, at 02:24, Jack Park  wrote:
>>>
>>> 
>>> The problem:
>>>
>>> In Java, I have an interface *IInferrable* which is basically  boolean
>>> eval();
>>>
>>> Any Java object which extends IInferrable, no matter what it is, will
>>> answer to eval() and return a boolean.
>>> The idea lies at the heart of an inference engine.
>>>
>>> But, I also define a class *AndList* which implements IInferrable and
>>> extends java.util.ArrayList
>>>
>>> So, AndList, and its sibling OrList behave just like a List object, but
>>> also will answer to eval() by running the collection and dealing with what
>>> each element returns when it, too, is eval()'d.
>>>
>>> I'd really love to discover how to pull that off in Clojure.
>>>
>>>
>
> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/clojure/CACACo5TDpMg_CEhE2ytwZv9R1L3%3DifayFLYTs6KC80vON59hiw%40mail.gmail.com
> 
> .
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com

Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Jesús Gómez
Why not to Java-Interop with that Interface and those Classes directly, the
same way you use them in Java?

El jue., 13 ago. 2020 a las 22:54, Jack Park ()
escribió:

> The problem:
>
> In Java, I have an interface *IInferrable* which is basically  boolean
> eval();
>
> Any Java object which extends IInferrable, no matter what it is, will
> answer to eval() and return a boolean.
> The idea lies at the heart of an inference engine.
>
> But, I also define a class *AndList* which implements IInferrable and
> extends java.util.ArrayList
>
> So, AndList, and its sibling OrList behave just like a List object, but
> also will answer to eval() by running the collection and dealing with what
> each element returns when it, too, is eval()'d.
>
> I'd really love to discover how to pull that off in Clojure.
>
> Many thanks in advance. -Jack
>
> --
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with
> your first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> ---
> You received this message because you are subscribed to the Google Groups
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/clojure/3e2ffc86-0e4f-4c0c-92c3-58e0848d5ba7o%40googlegroups.com
> 
> .
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CAO9z-97N15E_17FRkDN_gbneXfkMkrS615RV5UwGMf3%2Bos%3DSLQ%40mail.gmail.com.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Oleksandr Shulgin
On Fri, Aug 14, 2020 at 9:05 AM Oleksandr Shulgin <
oleksandr.shul...@zalando.de> wrote:

> On Fri, Aug 14, 2020 at 7:51 AM Alexandre Almosni <
> alexandre.almo...@gmail.com> wrote:
>
>> Maybe your objects could be defined by a map containing functions and
>> objects.
>>
>> So exampleAndList = {:fn and, :coll [a b c]}
>>
>>
>> And then eval goes through your objects recursively, using
>>
>> (def eval [o]
>> (apply (:fn o) (map eval (:coll o
>>
>> - with a special case that if o is not a map but say a Boolean you just
>> return itself
>>
>
> A slight problem with that approach is that clojure.core/and is not a
> function, but a macro: the reason being is that it stops evaluating forms
> as soon as it hits a falsey value (similar for "or").
> A smart implementation of And/OrList would like to short-circuit as well I
> guess, so you'll need to express that somehow.
>
> Of the clojure.core library that property is satisfied by transducers:
> https://clojure.org/reference/transducers#_early_termination
>

I came up with the following:

;; and-transducer with early termination:
 (defn xand [rf]
   (fn
 ([] (rf))
 ([res] (rf res))
 ([res inp] (if inp
  (rf res inp)
  (reduced inp)

;; reducing function implementing and:
  (defn andr
   ([] true)
   ([i] i)
   ([r i] (and r i)))

;; noisy variant of get:
 (defn noisy-get
  ([k]
   (fn [m]
 (noisy-get m k)))
  ([m k]
   (println "noisy-get" m k)
   (get m k)))

;; all in action:
user> (def xf (comp (map (noisy-get :data))
xand))
#'user/xf
user> (transduce xf andr [{:data 1} {:data false} {:no-data 3}])
noisy-get {:data 1} :data
noisy-get {:data false} :data
false
user> (transduce xf andr [{:data 1} {:data 2} {:no-data 3} {:data 4}])
noisy-get {:data 1} :data
noisy-get {:data 2} :data
noisy-get {:no-data 3} :data
nil
user> (transduce xf andr [{:data 1} {:data 2} {:data 3} {:data 4}])
noisy-get {:data 1} :data
noisy-get {:data 2} :data
noisy-get {:data 3} :data
noisy-get {:data 4} :data
4

It does feel a bit redundant to have the reducing function on top of a
transducer that accomplishes mostly the same, but I haven't found a way to
make it shorter.

Cheers,
--
Alex

> On 14 Aug 2020, at 02:24, Jack Park  wrote:
>>
>> 
>> The problem:
>>
>> In Java, I have an interface *IInferrable* which is basically  boolean
>> eval();
>>
>> Any Java object which extends IInferrable, no matter what it is, will
>> answer to eval() and return a boolean.
>> The idea lies at the heart of an inference engine.
>>
>> But, I also define a class *AndList* which implements IInferrable and
>> extends java.util.ArrayList
>>
>> So, AndList, and its sibling OrList behave just like a List object, but
>> also will answer to eval() by running the collection and dealing with what
>> each element returns when it, too, is eval()'d.
>>
>> I'd really love to discover how to pull that off in Clojure.
>>
>>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CACACo5TDpMg_CEhE2ytwZv9R1L3%3DifayFLYTs6KC80vON59hiw%40mail.gmail.com.


Re: First post: how to mimic a Java List with types?

2020-08-14 Thread Oleksandr Shulgin
On Fri, Aug 14, 2020 at 7:51 AM Alexandre Almosni <
alexandre.almo...@gmail.com> wrote:

> Maybe your objects could be defined by a map containing functions and
> objects.
>
> So exampleAndList = {:fn and, :coll [a b c]}
>
>
> And then eval goes through your objects recursively, using
>
> (def eval [o]
> (apply (:fn o) (map eval (:coll o
>
> - with a special case that if o is not a map but say a Boolean you just
> return itself
>

A slight problem with that approach is that clojure.core/and is not a
function, but a macro: the reason being is that it stops evaluating forms
as soon as it hits a falsey value (similar for "or").
A smart implementation of And/OrList would like to short-circuit as well I
guess, so you'll need to express that somehow.

Of the clojure.core library that property is satisfied by transducers:
https://clojure.org/reference/transducers#_early_termination

Regards,
--
Alex

On 14 Aug 2020, at 02:24, Jack Park  wrote:
>
> 
> The problem:
>
> In Java, I have an interface *IInferrable* which is basically  boolean
> eval();
>
> Any Java object which extends IInferrable, no matter what it is, will
> answer to eval() and return a boolean.
> The idea lies at the heart of an inference engine.
>
> But, I also define a class *AndList* which implements IInferrable and
> extends java.util.ArrayList
>
> So, AndList, and its sibling OrList behave just like a List object, but
> also will answer to eval() by running the collection and dealing with what
> each element returns when it, too, is eval()'d.
>
> I'd really love to discover how to pull that off in Clojure.
>
>

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/CACACo5SqECEzLU-4VBBvB8J6xdi%3DqRpoqLjR4urhq7TBiB3mXA%40mail.gmail.com.


Re: First post: how to mimic a Java List with types?

2020-08-13 Thread Alexandre Almosni
Maybe your objects could be defined by a map containing functions and objects.

So exampleAndList = {:fn and, :coll [a b c]}


And then eval goes through your objects recursively, using

(def eval [o]
(apply (:fn o) (map eval (:coll o 

- with a special case that if o is not a map but say a Boolean you just return 
itself



> On 14 Aug 2020, at 02:24, Jack Park  wrote:
> 
> 
> The problem:
> 
> In Java, I have an interface IInferrable which is basically  boolean eval();
> 
> Any Java object which extends IInferrable, no matter what it is, will answer 
> to eval() and return a boolean.
> The idea lies at the heart of an inference engine.
> 
> But, I also define a class AndList which implements IInferrable and extends 
> java.util.ArrayList
> 
> So, AndList, and its sibling OrList behave just like a List object, but also 
> will answer to eval() by running the collection and dealing with what each 
> element returns when it, too, is eval()'d.
> 
> I'd really love to discover how to pull that off in Clojure.
> 
> Many thanks in advance. -Jack
> -- 
> You received this message because you are subscribed to the Google
> Groups "Clojure" group.
> To post to this group, send email to clojure@googlegroups.com
> Note that posts from new members are moderated - please be patient with your 
> first post.
> To unsubscribe from this group, send email to
> clojure+unsubscr...@googlegroups.com
> For more options, visit this group at
> http://groups.google.com/group/clojure?hl=en
> --- 
> You received this message because you are subscribed to the Google Groups 
> "Clojure" group.
> To unsubscribe from this group and stop receiving emails from it, send an 
> email to clojure+unsubscr...@googlegroups.com.
> To view this discussion on the web visit 
> https://groups.google.com/d/msgid/clojure/3e2ffc86-0e4f-4c0c-92c3-58e0848d5ba7o%40googlegroups.com.

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/4D1E5BB6-F34A-4379-A534-2B4F7B68CE18%40gmail.com.