Network Scala Filters without Overhead

I want to bundle a bunch of filters, but I don't want the overhead associated with creating multiple lists.

type StringFilter = (String) => Boolean

def nameFilter(value: String): StringFilter = 
    (s: String) => s == value

def lengthFilter(length: Int): StringFilter = 
    (s: String) => s.length == length

val list = List("Apple", "Orange")

The problem is that it builds a list after each filter:

list.filter(nameFilter("Apples")).filter(lengthFilter(5))

// list of string -> list of name filtered string -> list of name and length filtered string

I want to:

// list of string -> list of name and length filtered string

I will find out what filters are needed at runtime, so I have to add filters dynamically.

// Not sure how to implement add function.
val filterPipe: StringFilter = ???

// My preferred DSL (or very close to it)
filterPipe.add(nameFilter("Apples")
filterPipe.add(lengthFilter(5))

// Must have DSL
list.filter(filterPipe)

How can i implement filterPipe?

Is there a way to recursively AND filter conditions together in filterPipe (which itself is a StringFilter)?

+4
source share
3 answers

You can use withFilter:

list.withFilter(nameFilter("Apples")).withFilter(lengthFilter(5))...
+4
source

,

implicit class Predicate[A](val pred: A => Boolean) {
  def apply(x: A) = pred(x)

  def &&(that: A => Boolean) = new Predicate[A](x => pred(x) && that(x))
  def ||(that: A => Boolean) = new Predicate[A](x => pred(x) || that(x))
  def unary_! = new Predicate[A](x => !pred(x))
}

list.filter { (nameFilter("Apple") && lengthFilter(5)) (_) }

val list = List("Apple", "Orange", "Meat")
val isFruit = nameFilter("Apple") || nameFilter("Orange")
val isShort = lengthFilter(5)

list.filter { (isFruit && isShort) (_) }

, withFilter ,

+1

, ,

list.view.filter(nameFilter("Apples")).filter(lengthFilter(5))

, list .

+1

All Articles