The Predicates Library
The idea for this library sprang from the fact that I haven't seen any explicit support for functions that return boolean values in Scala itself. There is a generalization that we work with functions that return Booleans and any function which returns Booleans is just that, a function. However, something is lost when we work this way. This becomes apparently so when working with the ::filter and ::filterNot methods from IntroGenTraversableLike. Had there been explicit library support for Predicates then the language authors would never had thought to create two similarly named functions which conceptually do the same thing, filter a list of some type by a predicate condition. Instead they could have relied on an aptly named "Not" predicate function.
If it were only the lack of a "Not" function this library would not have happened. I would have been content to petition the language gods for its inclusion in 3.0+. We're also lacking the tools and language support to work with predicate expressions themselves. I hope that this small library helps authors create syntactically clear and precise code when working with predicates.
Scala uses the familiar three operands to denote predicate logic: &&, "and;" ||, "or;" and !, "not." These form the basis for more complex predicate expressions such as "nor" and "xor." Unfortunately, these functions work on the Boolean value produced from the evalution of the expression and not the expression itself. Therefore, it is difficult to create reusable, extendable and composible predicates with them unless we want to use judicious applications of boilerplate (something Scala is, in general, very light on.) What it Provides
To counter act this limiation within the standard library I've written what is, essentially, a predicate template a la Scala's Function* variants. Each Predicate (1-22, mirroring Function*) adds the following factory functions that create a new Predicates using predicate logic:
- and - The resulting predicate returns true iff both predicates are true, false otherwise.
- andNot - Similar to above except the second predicate is negated
- nand - The negated "and." The resulting predicate returns true iff both predicates are not true
- nor - The negated "or." The resulting predicate returns true iff both predicates are false
- or - The resulting predicate returns true if either predicate expression is satisfied.
- orNot - Similar to above except the second predicate is negated.
- xor - Exclusive "or." The resulting predicate returns true iff one of the predicates is true but not both.
I've also included a few helper objects:
- Always - 22 function variants which always return true.
- Never - 22 function variants which always return false.
- Not - 22 function variants which negative the enclosing Predicate expression.
- Is - 22 helper methods a la Haskel's Data.Function.Predicate to make predicate formation easier and more expressive.
Together, I hope that these methods reduce DRY and add a little syntactic sugar to make everyone's lives just a little easier.
This library is not a Prolog logic library or logic solver. It does not contain anything close to Clojure's fantastic What it Does not Providecore.logic which I highly recommend checking out even if it is written in a dirty dynamic language. It is not a truth engine or compile time evaluation engine.
Originally it contained my first attempt at adding in predicated application and compoisition (see: here). However, my implementation was non-optimal, too inflexible, and too narrow in focus to be much use to anyone. I've since removed it. It may come back, although as it's own library.