J'ai une trame de données, par exemple:
sub day
1 1
1 2
1 3
1 4
2 1
2 2
2 3
2 4
3 1
3 2
3 3
3 4
et je voudrais supprimer des lignes spécifiques qui peuvent être identifiées par la combinaison de sous et jour. Par exemple, disons que je voulais supprimer les lignes où sub = '1' et day = '2' et sub = 3 et day = '4'. Comment pourrais-je faire ça? Je me rends compte que je pourrais spécifier les numéros de ligne, mais cela doit être appliqué à une énorme trame de données qui serait fastidieuse à parcourir et à identifier chaque ligne.
DF[ ! ( ( DF$sub ==1 & DF$day==2) | ( DF$sub ==3 & DF$day==4) ) , ] # note the ! (negation)
Ou si sub est un facteur comme le suggère votre utilisation de guillemets:
DF[ ! paste(sub,day,sep="_") %in% c("1_2", "3_4"), ]
Pourrait également utiliser un sous-ensemble:
subset(DF, ! paste(sub,day,sep="_") %in% c("1_2", "3_4") )
(Et j'approuve l'utilisation de which
dans la réponse de Dirk lors de l'utilisation de "[" même si certains prétendent que ce n'est pas nécessaire.)
Cela se résume à deux étapes distinctes:
which()
data.frame
en excluant les indices de l'étape précédente.Voici un exemple:
R> set.seed(42)
R> DF <- data.frame(sub=rep(1:4, each=4), day=sample(1:4, 16, replace=TRUE))
R> DF
sub day
1 1 4
2 1 4
3 1 2
4 1 4
5 2 3
6 2 3
7 2 3
8 2 1
9 3 3
10 3 3
11 3 2
12 3 3
13 4 4
14 4 2
15 4 2
16 4 4
R> ind <- which(with( DF, sub==2 & day==3 ))
R> ind
[1] 5 6 7
R> DF <- DF[ -ind, ]
R> table(DF)
day
sub 1 2 3 4
1 0 1 0 3
2 1 0 0 0
3 0 1 3 0
4 0 2 0 2
R>
Et nous voyons que sub==2
n'a plus qu'une entrée avec day==1
.
Edit La condition composée peut être effectuée avec un 'ou' comme suit:
ind <- which(with( DF, (sub==1 & day==2) | (sub=3 & day=4) ))
et voici un nouvel exemple complet
R> set.seed(1)
R> DF <- data.frame(sub=rep(1:4, each=5), day=sample(1:4, 20, replace=TRUE))
R> table(DF)
day
sub 1 2 3 4
1 1 2 1 1
2 1 0 2 2
3 2 1 1 1
4 0 2 1 2
R> ind <- which(with( DF, (sub==1 & day==2) | (sub==3 & day==4) ))
R> ind
[1] 1 2 15
R> DF <- DF[-ind, ]
R> table(DF)
day
sub 1 2 3 4
1 1 0 1 1
2 1 0 2 2
3 2 1 1 0
4 0 2 1 2
R>
Voici une solution à votre problème en utilisant la fonction filter
de dplyr .
Bien que vous puissiez passer votre bloc de données comme premier argument à n'importe quelle fonction dplyr, j'ai utilisé son %>%
, qui canalise votre bloc de données vers une ou plusieurs fonctions dplyr (filtrez simplement dans ce cas).
Une fois que vous êtes un peu familier avec dplyr, le aide-mémoire est très pratique.
> print(df <- data.frame(sub=rep(1:3, each=4), day=1:4))
sub day
1 1 1
2 1 2
3 1 3
4 1 4
5 2 1
6 2 2
7 2 3
8 2 4
9 3 1
10 3 2
11 3 3
12 3 4
> print(df <- df %>% filter(!((sub==1 & day==2) | (sub==3 & day==4))))
sub day
1 1 1
2 1 3
3 1 4
4 2 1
5 2 2
6 2 3
7 2 4
8 3 1
9 3 2
10 3 3
une solution simple
cond1 <- df$sub == 1 & df$day == 2
cond2 <- df$sub == 3 & df$day == 4
df <- df[!cond1,]
df <- df[!cond2,]