(Ted Harding) Ted.Harding at manchester.ac.uk
Thu Aug 13 21:50:54 CEST 2009

```On 13-Aug-09 19:21:36, David Huffer wrote:
> When adding several logical vectors I expect each vector will be
> coerced to integers and these vectors will then be added.
>
> That doesn't always seem to be the case.
>
> For example:
>
>   > ( f1 <- as.factor ( sample ( "x" , 25 , rep = T ) ) )
>    [1] x x x x x x x x x x x x x x x x x x x x x x x x x
>   Levels: x
>   > ( f2 <- as.factor ( sample ( "y" , 25 , rep = T ) ) )
>    [1] y y y y y y y y y y y y y y y y y y y y y y y y y
>   Levels: y
>   > ( f3 <- as.factor ( sample ( "z" , 25 , rep = T ) ) )
>    [1] z z z z z z z z z z z z z z z z z z z z z z z z z
>   Levels: z
>   >
>   > is.na ( f1 [ sample ( 1:25 , 4 ) ] ) <-
>   + is.na ( f2 [ sample ( 1:25 , 4 ) ] ) <-
>   + is.na ( f3 [ sample ( 1:25 , 4 ) ] ) <- TRUE
>   >
>   > ##  this returns a numeric vector:
>   >
>   > is.na ( f1 ) + is.na ( f2 ) + is.na ( f3 )
>    [1] 0 0 0 0 0 1 1 0 0 0 1 0 0 1 0 0 1 0 1 2 2 0 1 0 1
>   >
>   > ##  but this returns a logical vector
>   >
>   > !is.na ( f1 ) + !is.na ( f2 ) + !is.na ( f3 )
>    [1]  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE
>    [9]  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE  TRUE
>   [17] FALSE  TRUE FALSE  TRUE FALSE  TRUE FALSE  TRUE
>   [25] FALSE
>   >
>
> Can someone please explain why the returned value is a logical
> vector when I use the not operator but a numeric vector when I
> don't.
>
> What is special about the !is.na? it returns an object of class
> logical just like the is.na function:
>
>   > all.equal ( class ( !is.na ( f1 ) ) , class ( is.na ( f1 ) ) )
>   [1] TRUE
>   >
>
> Thanks!

I think you need to compare:
[1]
is.na ( f1 ) + !is.na ( f2 )
# [1] 2 0 1 1 2 1 0 1 1
#[10] 1 0 2 1 1 0 1 1 2
#[19] 1 1 1 1 1 1 1

with
[2]
!is.na ( f1 ) + !is.na ( f2 )
# [1] FALSE  TRUE FALSE FALSE FALSE FALSE  TRUE FALSE FALSE
#[10] FALSE  TRUE FALSE FALSE FALSE  TRUE FALSE FALSE FALSE
#[19] FALSE FALSE FALSE FALSE FALSE FALSE FALSE

and with
[3]
(!is.na ( f1 )) + (!is.na ( f2 ))
# [1] 1 1 2 2 1 2 1 2 2 2 1 1 2 2 1 2 2 1 2 2 2 2 2 2 2

In other words, I think you have been trapped by Precedence:
see '?Syntax'. What seems to happen is that

is.na ( f1 ) + !is.na ( f2 )

evalutes is.na(f1) as a logical vector, !is.na(f2) as a logical
vector, and adds them getting a numerical result. See [1].

On the other hand, apparently

!is.na ( f1 ) + !is.na ( f2 )

negates the result of [1] (compare the outputs of [1] and [2])
and hence produces a logical vector (because of the first "!").
In other words, the first "!" is applied to the result of
is.na ( f1 ) + !is.na ( f2 ).

In the form given in [3], the parentheses ensure that the logical
negations "!" are applied before the "+" is applied, so two logical
vectors are added, with a numerical result.

(I hope I've got this right)!
Ted.

--------------------------------------------------------------------
E-Mail: (Ted Harding) <Ted.Harding at manchester.ac.uk>
Fax-to-email: +44 (0)870 094 0861
Date: 13-Aug-09                                       Time: 20:50:51
------------------------------ XFMail ------------------------------

```