Come combinare più condizioni per creare un sottoinsieme di un frame di dati usando “OR”?


174

Ho un data.frame in R. Voglio provare due condizioni diverse su due colonne diverse, ma voglio che queste condizioni siano inclusive. Pertanto, vorrei utilizzare "OR" per combinare le condizioni. Ho usato la seguente sintassi prima con molto successo quando volevo usare la condizione "AND".

my.data.frame <- data[(data$V1 > 2) & (data$V2 < 4), ]

Ma non so come usare un 'OR' sopra.

Risposte:


249
my.data.frame <- subset(data , V1 > 2 | V2 < 4)

Una soluzione alternativa che imita il comportamento di questa funzione e sarebbe più appropriata per l'inclusione in un corpo di funzione:

new.data <- data[ which( data$V1 > 2 | data$V2 < 4) , ]

Alcune persone criticano l'uso whichcome non necessario, ma impedisce ai NAvalori di restituire risultati indesiderati. L'equivalente (.ie non restituisce le righe NA per qualsiasi NA in V1 o V2) alle due opzioni sopra dimostrate senza il whichsarebbe:

 new.data <- data[ !is.na(data$V1 | data$V2) & ( data$V1 > 2 | data$V2 < 4)  , ]

Nota: voglio ringraziare il collaboratore anonimo che ha tentato di correggere l'errore nel codice immediatamente sopra, una correzione che è stata respinta dai moderatori. Si è effettivamente verificato un ulteriore errore che ho notato durante la correzione del primo. La clausola condizionale che controlla i valori di NA deve essere la prima se deve essere gestita come volevo, dal momento che ...

> NA & 1
[1] NA
> 0 & NA
[1] FALSE

L'ordine degli argomenti può essere importante quando si utilizza '& ".


1
Questa è la più alta domanda votato e poi uno reperti: stackoverflow.com/questions/9860090/...
PatrickT

1
Il vantaggio è la compattezza e la facilità di comprensione. Lo svantaggio è la mancanza di utilità nelle attività di costruzione delle funzioni. Se uno vuole replicare questo con [uno deve avvolgere whicho usare !is.navincoli aggiuntivi .
IRTFM,

È richiesto il 'quale' e, in caso contrario, perché lo usi?
Cleb,

1
Non è "obbligatorio", ma è possibile ottenere un risultato diverso se si lascia fuori which. Se sia V1 che V2 sono NA, otterresti una fila di NA in quella posizione se avessi lasciato fuori which. Lavoro con set di dati di grandi dimensioni e anche una percentuale relativamente piccola di NA riempie il mio schermo con output spazzatura. Alcune persone pensano che questa sia una caratteristica. Io non.
IRTFM,

come si include una chiamata a greplo grepcon questo per fare anche la corrispondenza del modello per le righe desiderate, oltre a questi condizionali?
user5359531

31

Stai cercando "|." Vedi http://cran.r-project.org/doc/manuals/R-intro.html#Logical-vectors

my.data.frame <- data[(data$V1 > 2) | (data$V2 < 4), ]

Questo NON è NAaffidabile per l'esistenza di s in un dataframe:vc <- data.frame(duzey=factor(c("Y","O","Y","D","Y","Y","O"), levels=c("D","O","Y"), ordered=TRUE), cinsiyet=c("E","E","K",NA,"K","E","K"), yas=c(8,3,9,NA,7,NA,6), Not=c(NA,1,1,NA,NA,2,1)); vc; vc[vc$cinsiyet == "E" | vc$Not < 4,]; vc[vc$cinsiyet == "E" & vc$Not < 2,]
Erdogan CEVHER

17

Solo per completezza, possiamo usare gli operatori [e [[:

set.seed(1)
df <- data.frame(v1 = runif(10), v2 = letters[1:10])

Diverse opzioni

df[df[1] < 0.5 | df[2] == "g", ] 
df[df[[1]] < 0.5 | df[[2]] == "g", ] 
df[df["v1"] < 0.5 | df["v2"] == "g", ]

df $ name è equivalente a df [["" name ", esatta = FALSO]]

Utilizzando dplyr:

library(dplyr)
filter(df, v1 < 0.5 | v2 == "g")

Utilizzando sqldf:

library(sqldf)
sqldf('SELECT *
      FROM df 
      WHERE v1 < 0.5 OR v2 = "g"')

Output per le opzioni sopra:

          v1 v2
1 0.26550866  a
2 0.37212390  b
3 0.20168193  e
4 0.94467527  g
5 0.06178627  j

1
come faresti per 1 condizione AND e 3 condizioni contingenti, ad esempio: my.data.frame <- data [data $ V3> 10 & ((data $ V1> 2) | (data $ V2 <4) | (data $ V4 <5),]. Quando lo faccio non funziona
R Guru

1
Wow! Il sqldfpacchetto è troppo buono. Molto utile soprattutto quando subset()diventa un po 'doloroso :)
Dawny33
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.