Avoid IF Statements for Faster Operation
It pays to attempt to code as much as possible of each program in array expressions, avoiding scalars, loops, and IF statements. Some examples of slow and fast ways to achieve the same results are:
Example 1
Add all positive elements of B to A:
; Slow way uses a loop.
FOR I = 0, (N - 1) DO IF B(I) GT 0 THEN
A(I) = A(I) + B(I)
; Fast way: Mask out negative elements using array operations.
A = A + (B GT 0) * B
; Faster way: Add B > 0.
A = A + (B > 0)
Example 2
Often an IF statement appears in the middle of a loop, with each element of an array in the conditional. By using logical array expressions, the loop may sometimes be eliminated.
Set each element of C to the square-root of A if A(I) is positive, otherwise, set C(I) to minus the square-root of A(I):
; Slow way uses an IF statement.
FOR I = 0, (N - 1) DO IF A(I) LE 0 THEN
C(I) = -SQRT(-A(I)) ELSE
C(I) = SQRT(A(I))
; Fast way.
C = ((A GT 0) * 2 - 1) * SQRT(ABS(A))
For a 10,000-element floating-point vector, the statement using the IF took 8.5 seconds to execute, while the version using the array operation took only 0.7 seconds.
The expression (A GT 0) has the value of 1 if A(I) is positive and is 0 if A(I) is not. (A GT 0) * 2 – 1 is equal to +1 if A(I) is positive or minus 1 if A(I) is negative, accomplishing the desired result without resorting to loops or IF statements.
Another method is to use the WHERE function to determine the subscripts of the negative elements of A and negate the corresponding elements of the result:
; Get subscripts of negative elements.
NEGS = WHERE (A LT 0)
; Take root of absolute value.
C = SQRT(ABS(A))
; Fix up negative elements.
C(NEGS) = -C(NEGS)
This version took 0.8 seconds to process the same 10,000-element floating-point array.
Version 2017.0
Copyright © 2017, Rogue Wave Software, Inc. All Rights Reserved.