Soy nuevo y estoy aprendiendo R. Estoy tratando de hacer una pregunta para la que no sé las palabras. Supongamos que tengo un marco de datos tal que:

df<-data.frame(ID=c("A","A","A","B","B","B","C","C","C"),
Week=c(1,2,3,1,2,3,1,2,3),
Variable=c(30,25,27,42,44,45,30,50,19))



  ID Week Variable
1  A    1       30
2  A    2       25
3  A    3       27
4  B    1       42
5  B    2       44
6  B    3       45
7  C    1       30
8  C    2       50
9  C    3       19

¿Cómo puedo encontrar cuál es la variable promedio en la semana 2 para todas las ID que tenían variable = 30 en la semana 1?

Por ejemplo, me gustaría que la salida en este ejemplo sea = 37.5

r
0
Absolute_Human 15 sep. 2018 a las 22:25

3 respuestas

La mejor respuesta

Paso 1: Obtenga los ID que tenían Variable = 30 en la Semana1

res<-  subset( df,Variable==30 & Week==1, ID ) 

La salida es:

> res
  ID
1  A
7  C

Paso 2: Obtenga todas sus variables en la semana 2:

dt<-subset(df,ID %in% as.vector(unlist(res))  & Week==2  ,select=c(ID,Variable))

La salida es:

  ID Variable
2  A       25
8  C       50

Paso 3: Obtenga el significado:

  mean(dt$Variable)

El resultado final es:

37.5

En el paso 2 tenemos ID %in% as.vector(unlist(res)). Entonces, ¿qué significa?

La parte% en% simplemente es un operador que devuelve verdadero si encuentra una ID dentro del vector derecho. Por ejemplo, ejecute la siguiente muestra:

  a<- 1:10

  b<-c(0,4,6,8,16)

  b %in% a

Y el resultado es:

FALSE  TRUE  TRUE  TRUE FALSE

Por lo tanto, el operador% en% devuelve un valor booleano para cada elemento de b. El resultado será True si ese elemento existe en a, de lo contrario, devuelve False . Como ves 0 y 16 tienen False.

Pero, el punto es que a debe ser un vector, mientras que res es un data.frame, así que primero tengo que unlist y luego considerarlo como {{X4 }} (as.vector).

En conclusión, ID %in% as.vector(unlist(res)) verifica si cada ID existe en res o no.

0
Salman Lashkarara 15 sep. 2018 a las 21:19

Esto podría ser más fácil de leer / ver.

library(tidyverse)

df %>% 
  spread(Week, Variable) %>%
  filter(`1` == 30) %>%
  with(mean(`2`))

[1] 37.5

Creo que el código tidyverse es más fácil de entender porque puede leerlo de izquierda a derecha como lo haría con cualquier texto sin código. Y la canalización %>% hace que sea más fácil ver el orden de las operaciones, no más paréntesis para analizar.

1
Nate 15 sep. 2018 a las 20:08

Primero necesitamos ID 's que tienen entrada para variable=30 AND week=1 y luego de ese ID' s extracto ID 's con Week=2 y hacer {{X5} }

Solución Base R:

mean(df[df$ID %in% (df[df$Week==1 & df$Variable==30,1]) & df$Week==2,3])

Salida:

[1] 37.5

O (otro enfoque)

Usando sqldf:

library(sqldf)
sqldf("select avg(Variable) from df where ID IN (select ID from df where variable=30 AND week=1) AND Week=2")

Salida:

    avg(Variable)
1          37.5
0
Saurabh Chauhan 15 sep. 2018 a las 19:45