ALL and ANY words
[1/5] from: info::id-net::ch at: 4-Jan-1980 3:58
The All word is often used by some rebolwriters in this case : all [select
nam word find text search-text , etc..].. I mean : it is used with more
than 2 parameter, and often with not always a TRUE OR FALSE' return (it
seems...). It is done very often by Carl ..
Personnally, I used 'all and 'any , in those cases : all [(a > 0)(b > 0)],
i.e.
It seems that the 'all and 'any word are used in a area that is different..
Is it like the C langage when FALSE is zero and all other cases TRUE..
I understand that a function like SELECT (taken as exemple above) could
return true of false.. It's not the point..
I just want to know if the values that 'all evaluate can be other than true
or false..
Philippe
[2/5] from: carl:cybercraft at: 2-Feb-2003 1:19
Hi Philippe,
On 04-Jan-80, Philippe Oehler wrote:
> The All word is often used by some rebolwriters in this case : all
> [select nam word find text search-text , etc..].. I mean : it is
<<quoted lines omitted: 8>>
> I just want to know if the values that 'all evaluate can be other
> than true or false..
Yes, the results can be other than true or false (or none). With ALL,
each expression in the block is evaluated in turn, unless one returns
FALSE or NONE, at which point the rest of the expressions are
ignored.
ie, here no NONE or FALSE values are returned...
>> all [print "a" 1 = 1 print "b" 2 = 2 print "c" 3 = 3]
a
b
c
== true
but here the 2 = 3 is false, so that's as far as the evaluation
gets...
>> all [print "a" 1 = 1 print "b" 2 = 3 print "c" 3 = 3]
a
b
== none
With ANY, the block is evaluated until the first true (or non-none or
non-false, if you will) is returned, at which point the rest of the
evaluations are skipped.
ie, here nothing is true...
>> any [1 = 2 3 = 4 5 = 6]
== none
while here the print "a" is considered true so evaluation stops there
and doesn't reach the print "b"...
>> any [1 = 2 3 = 4 print "a" 5 = 6 print "b"]
a
HTH.
--
Carl Read
[3/5] from: info::id-net::ch at: 4-Jan-1980 6:14
Ok.. I understand now.. With ALL, you can make a lots of stuff, with
conditions checks, and break opportunities, without using long structures of
IF.. it's cool
[4/5] from: joel:neely:fedex at: 1-Feb-2003 10:09
Hi, Philippe,
TMTOWTUT -- There's more than one way to use them...
(with apologies to Perlophobes ;-)
Philippe Oehler wrote:
> Ok.. I understand now.. With ALL, you can make a lots of stuff,
> with conditions checks, and break opportunities, without using
> long structures of IF.. it's cool
>
ALL can play the role of a generalized AND ...
all [a b c ... z]
evaluates A and B and C and ... Z in order, but quits as soon as
a FALSE or NONE value is encountered (in which case it returns
NONE -- instead of FALSE, which is a bit counter-intuitive IMHO).
<MILDSURPRISE>
UNSET! is neither FALSE nor NONE, and therefore allows ALL
to continue evaluation, as in
>> type? all [print 1 print true print false]
1
true
false
== unset!
</MILDSURPRISE>
Given that the expression
if cond expr
yields NONE if COND evaluates false, and otherwise the value of
evaluating EXPR, ALL can be combined with IF in interesting ways:
>> a: 1 b: 2 c: 3
== 3
>> if all [
[ if a < b [print "a:b in order"]
[ if b < c [print "b:c in order"]
[ true
[ ] [print "all in order"]
a:b in order
b:c in order
all in order
>>
IOW, ALL can be used to sequence/control subordinate actions, with
bailout
conditions to interrupt/abort the sequence of actions.
As for ANY, it can serve as a generalized OR, as in:
any [a b c ... z]
which quits as soon as a value that is neither FALSE nor NONE is
encountered in evaluation (same MILDSURPRISE previously noted
applies here as well).
Therefore a common idiom is to use ANY to establish default values.
var: any [expr0 expr1 ... defaultexpr]
so that the first subexpression that yields a (non-FALSE, non-NONE)
value will supply the value for VAR, and DEFAULTEXPR will supply the
one if no others work:
class: any [
if find seniors studentID ["senior"]
if find juniors studentID ["junior"]
if find sophomores studentID ["sophomore"]
if find freshmen studentID ["freshman"]
"unregistered"
]
One (slightly contrived) example is to detect cases where variables
have (intentionally) never been initialized, as in the infamous
first time through a loop
case. Suppose we want to determine
whether a block of numbers is in ascending order. We could write
this in a fairly boring way:
catch [
use [old] [
old: block-o-nums/1
foreach new block-o-nums [
if new < old [throw false]
old: new
]
true
]
]
or use ANY to handle the initialization issue for us:
catch [
use [old] [
old: none
foreach new block-o-nums [
if new < any [old new] [throw false]
old: new
]
true
]
]
(I said it was contrived! ;=-) The point is that we can use ANY and
ALL to do all sorts of interesting tricks. Having options is nice!
-jn-
[5/5] from: tomc:darkwing:uoregon at: 1-Feb-2003 14:06
'any & 'all are "short circut" versions of 'or & 'and
and can be used to protect some code from execution
an example to show how the "short-circut 'and" ('all)
differs from the normal 'and consider
>> a: 0
== 0
>> if (a <> 0) and (1 / a) [print "whatever"]
** Math Error: Attempt to divide by zero
** Where: do-boot
** Near: 1 / a
>> if all[(a <> 0) (1 / a)] [print "whatever"]
== none
in the second case the (1 / a) was never reached due to the short circut.
On Fri, 4 Jan 1980, Philippe Oehler wrote:
Notes
- Quoted lines have been omitted from some messages.
View the message alone to see the lines that have been omitted