Quick question for clarity. I assume that
compose [ 1 (1 / 0) 3 ]
would be a math error. Why is
compose [ 1 (third [ 1 2 ]) 3 ]
not some kind of a range check error?
Quick question for clarity. I assume that
compose [ 1 (1 / 0) 3 ]
would be a math error. Why is
compose [ 1 (third [ 1 2 ]) 3 ]
not some kind of a range check error?
Systemically, we consider NULL to be a "soft" form of failure. It serves a signaling role that's a little like what NONE! tried to do in historical Rebol, but since it's not an ANY-VALUE! more functions treat it as an error:
>> third [1 2]
; null
>> append [a b c] third [1 2]
** Script Error: append requires value argument to not be null
The theory is that places which require an ANY-VALUE! will error down the line, and that having a lot of constructs that make it easier to react to the "soft failure" is a better tradeoff.
There are a lot of options for handling it:
; x will be blank if either the third element was a blank or if there was
; no third element. Branch won't run if third element is falsey.
;
if x: try third [1 2] [...branch does not run...]
if x: try third [1 2 #[false]] [....branch does not run...]
; x will be null if there was no third element, and branch would run even
; if there was a falsey element in the third slot.
;
if did x: third [1 2] [...branch does not run....]
if did x: third [1 2 #[false]] [...branch runs...]
x: third [1 2] then [...branch does not run...]
x: third [1 2 #[false]] then [...branch runs...]
Experience has borne out that soft failure is a more convenient for functions like THIRD than raising an error. If anyone finds a case where they don't think so, I'd be interested to see it.