Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Best functional approach to AND across a list

Tags:

ruby

Suppose I have an array of values [a,b,c,d,...] and a function f(x,...) which returns true or false.

[1,2,3,4].map {|x| f(x)}  => [true true false true]

First, what is the best way to collapse the resultant list into a true or false value (via AND)? Is there a function that would allow me to map:

[true true false true]

to:

((true && true) && false) && true

using a cumulative pair-wise application of the binary && operator?

In this case the cost of evaluating the function is substancial, so would like to use a lisp-style "and" to evaluate the arguments (function applications) sequentially until one of them is false. Determined that could do:

!![1,2,3,4].each {|x| break false if !f(x) }

Which is ugly. Hoping that there is a more elegant way to do this. I am aware that I could add a new comprehension to Array, but hoping that there is something built-in that does this better. Thanks

like image 415
Jonathan Shore Avatar asked Mar 01 '10 13:03

Jonathan Shore


People also ask

Which functional programming language is best?

#1) Clojure Best for people looking for a compiled general-purpose functional programming language and something that's fully compatible with JVM.

What is functional programming approach?

Functional programming is a programming paradigm in which we try to bind everything in pure mathematical functions style. It is a declarative type of programming style. Its main focus is on “what to solve” in contrast to an imperative style where the main focus is “how to solve”.

What is functional programming best used for?

Functional Programming is used in situations where we have to perform lots of different operations on the same set of data. Lisp is used for artificial intelligence applications like Machine learning, language processing, Modeling of speech and vision, etc.


1 Answers

You're looking for Enumerable#all?, which returns true if all of the invocations of its block are truthy. There is also Enumerable#any?, which returns true if any of the invocations of its block are truthy:

#!/usr/bin/ruby1.8

def even(n)
  n % 2 == 0
end

p [1, 2, 3, 4].all? { |i| even(i) }    # => false
p [2, 4, 6, 8].all? { |i| even(i) }    # => true
p [1, 2, 3, 4].any? { |i| even(i) }    # => true
p [1, 3, 5, 7].any? { |i| even(i) }    # => false

any? short-curcuits: the first truthy value causes it to return true. So does all? short circuit: the first falsy value causes it to return false.

like image 200
Wayne Conrad Avatar answered Nov 09 '22 00:11

Wayne Conrad