[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Not where



Kenneth P. Bowman <bowman@null.edu> wrote in message
bowman-0702000905130001@bowman.tamu.edu">news:bowman-0702000905130001@bowman.tamu.edu...
> I often find myself using WHERE to divide an array into two parts.  I do
> one operation on the first part and a different operation on the second
> part.
>
> It would be nice to have an auxiliary array containing all the indices
> that are *not* returned by WHERE in i.  For example, it would be nice to
> do
>
> a = FLTARR(...)
> i = WHERE((a...), count, NOT_WHERE = j, NOT_COUNT = not_count)
> IF (count     GT 0L) THEN a[i] = ...
> IF (not_count GT 0L) THEN a[j] = ...
>
> Lacking the above changes to WHERE, can anyone suggest a fast and easy way
> to get j=NOT(i) ?

Strange: I was just thinking about this last week. The following approach is
easy, but costs two WHEREs:

First, create an array of Boolean operator results (0=false, 1=true):

arr = indgen(10)
test = arr gt 5
print, test
   0   0   0   0   0   0   1   1   1   1

Then use WHERE to locate the true and false values:

true_index = where(test ne 0, true_count)
false_index = where(test eq 0, false_count)
help, true_count, false_count
TRUE_COUNT      LONG      =            4
FALSE_COUNT     LONG      =            6
print, true_index
           6           7           8           9
print, false_index
           0           1           2           3           4           5

To implement this as a WHERE-like function:

FUNCTION MYWHERE, TEST, TRUE_COUNT, $
  FALSE_INDEX=FALSE_INDEX, FALSE_COUNT=FALSE_COUNT
if (n_elements(test) eq 0) then message, 'Argument TEST is undefined'
true_index = where(test ne 0, true_count)
if arg_present(false_index) or arg_present(false_count) then $
  false_index = where(test eq 0, false_count)
return, true_index
END

true_index = mywhere(arr gt 5, true_count)
print, true_count, true_index
           4
           6           7           8           9
true_index = mywhere(arr gt 5, true_count, $
  false_index=false_index, false_count=false_count)
IDL> print, false_count, false_index
           6
           0           1           2           3           4           5

Cheers,
Liam.
http://cimss.ssec.wisc.edu/~gumley