user1482923 - 7 months ago 38

R Question

I'm trying to perform a function to each cell of a data table in R, creating a second one based on the result of this loop.. For example, imagine I have Matrix A

`Ad1 Ad2 Ad3 Ad4`

AA 6 0 10

AB 7 10 12

AC 0 0 15

and I'm trying to create Matrix B

`Ad1 Ad2 Ad3 Ad4`

AA 1 0 1

AB 1 0 1

AC 0 0 1

in a way that each cell assumes the value 1 if that cell has a value > 0

For instance, AA~Ad2 is 6 and the sum of the column is 7 (6 + 7 + 0 - 6); then AA~Ad2 in matrix B assumes value 1.

Is there a way to perform this without performing a loop? I've managed to do this with a loop but it is taking too long:

`A = read.table(text="Ad1 Ad2 Ad3 Ad4`

AA 6 0 10

AA 7 10 12

AA 0 0 15", header=TRUE)

B = read.table(text="Ad1 Ad2 Ad3 Ad4

AA 0 0 0

AA 0 0 0

AA 0 0 0", header=TRUE)

for (i in 1:nrow(B)) {

for (j in 2:ncol(B)) {

if ((sum(A[,j], na.rm = T) - ifelse(is.na(A[i,j]), 0, A[i,j]))> 0 &

ifelse(is.na(A[i,j]), 0, A[i,j]) > 0 )

{B[i,j] <- 1}

}

}

Answer

We can do this without a loop by creating two logical matrices -1) check whether the numeric column values are greater than 0 (`A[-1] > 0`

), 2) check whether the difference of the column sums with the column values are also greater than 0. If both of them are TRUE (`&`

condition), convert the logical matrix to binary (`+`

) and assign it to the subset of the dataset (`A[-1]`

)

```
A[-1] <- +(colSums(A[-1])[col(A[-1])]-A[-1]>0 & A[-1] > 0)
A
# Ad1 Ad2 Ad3 Ad4
#1 AA 1 0 1
#2 AB 1 1 1
#3 AC 0 0 1
```

Source (Stackoverflow)