Idioms for filtering an array given a predicate?

98 views
Skip to first unread message

Ray Toal

unread,
Dec 31, 2015, 7:53:15 PM12/31/15
to Kona Users
Here is on technique for summing the squares of the odd numbers of an array:

  a: 5 8 7 2 3 4 1 9

5 8 7 2 3 4 1 9

  +/((a!2)*a)^2

165.0


This works because


  a

5 8 7 2 3 4 1 9

  a!2

1 0 1 0 1 0 1 1

  (a!2)*a

5 0 7 0 3 0 1 9

  ((a!2)*a)^2

25 0 49 0 9 0 1 81.0

  +/((a!2)*a)^2

165.0


This approach does not work by first filtering the odd numbers then squaring them then reducing the plus function over them. Instead it relies on turning odd numbers into 1s and even numbers into 0s and then multiplying by the original array. This hack basically preserves all odd numbers and turns even numbers into zeros. I knew this would be okay because I was ultimately going to sum them up.


Is this even a hack though? No array ever got reshaped so maybe this is a good approach?


But what if I just wanted to implement, in K, a function that selected only those elements for which a predicate was true (called filter in other languages, and select in Ruby)?


In other words, how does one write, or _should one write_, something that can do this:


  filter {x!2} 5 8 7 2 3 4 1 9

5 7 3 1 9


I looked to see if such a function existed but did not find anything, even on this reference card https://kx.com/technical/contribs/mikep/ReferenceCard.PDF or even in the Kona examples. Did I miss anything? Or is filter not something we normally do? Can indexing operations be done with functions?


Kevin Lawler

unread,
Dec 31, 2015, 8:54:15 PM12/31/15
to kona...@googlegroups.com
  filter: {y[&x@/:y]}
  
  filter[{x!2} ; 5 8 7 2 3 4 1 9]
5 7 3 1 9
  
  filter[![;2] ; 5 8 7 2 3 4 1 9]
  {x!2} filter\:  5 8 7 2 3 4 1 9

k5 promotes filter to a built in. function argument to reshape.

i've seen it requested a lot more lately. historically i haven't seen it used much. but maybe that's because we didn't have it.


--
You received this message because you are subscribed to the Google Groups "Kona Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to kona-user+...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Ray Toal

unread,
Dec 31, 2015, 11:12:24 PM12/31/15
to Kona Users
Thanks! Using @ over / is the insight I missed.

Interesting that requests are coming in for this.... I thought that maybe in traditional K applications it was not common, despite it being in nearly every other modern language. I did not know it was built-in in K5.

Ryan Gonzalez

unread,
Dec 31, 2015, 11:23:34 PM12/31/15
to kona...@googlegroups.com, Kevin Lawler


On December 31, 2015 7:53:55 PM CST, Kevin Lawler <kevin....@gmail.com> wrote:
> filter: {y[&x@/:y]}
>
> filter[{x!2} ; 5 8 7 2 3 4 1 9]
>5 7 3 1 9
>
> filter[![;2] ; 5 8 7 2 3 4 1 9]
> {x!2} filter\: 5 8 7 2 3 4 1 9
>

Wow, that's neat. I always did {x@&y'x}.
--
Sent from my Nexus 5 with K-9 Mail. Please excuse my brevity.

Ray Toal

unread,
Jan 1, 2016, 12:21:01 AM1/1/16
to Kona Users, kevin....@gmail.com
Yep, just found that one on Rosetta Code http://rosettacode.org/wiki/Filter#K (didn't think of looking there at first)

Kevin Lawler

unread,
Jan 1, 2016, 2:31:53 PM1/1/16
to kona...@googlegroups.com

On Thu, Dec 31, 2015 at 8:12 PM, Ray Toal <ray....@gmail.com> wrote:
Interesting that requests are coming in for this.... I thought that maybe in traditional K applications it was not common, despite it being in nearly every other modern language. I did not know it was built-in in K5.

The two natural objections to it are:

1. Running a lambda on each element of a list is several times slower than working with a list using array language primitives.

2. Without showing this in detail, I think that the objectives of filter are more usually accomplished by these direct methods, as your original example would indicate.

Which is not a commentary on any of its positive benefits.

Ray Toal

unread,
Jan 2, 2016, 5:11:28 PM1/2/16
to Kona Users
I did suspect that filtering was more of a concept that shows up in other contexts rather than being something requiring a built-in. I'm starting to like that indexing-with-a-where style, and have used it to get rid of my dumb multiplication hack, and now feel like I have more idiomatic K:

  sumofevensquares: {+/x[&~x!2]^2}


{+/x[&~x!2]^2}


  sumofoddsquares: {+/x[&x!2]^2}


{+/x[&x!2]^2}


  sumofevensquares (1,2,3,4,5,6)


56.0


  sumofoddsquares (1,2,3,4,5,6)


35.0

Steve Graham

unread,
Mar 22, 2019, 9:28:07 PM3/22/19
to Kona Users
Thanks for this, Kevin.  Steve


On Thursday, December 31, 2015 at 5:54:15 PM UTC-8, Kevin wrote:
Reply all
Reply to author
Forward
0 new messages