2017-04-07 3 views
0

ただ1つの観測値を含む因子からレベルを落とす単純な関数(drop.levelsに似ています)が存在するかどうかを知りたいと思います。私は以下の再現可能な例を提供します。今まで私はただ一つの観察でレベルを含む要因の名前を保存することができましたが、特定のレベルを落とすためにすべてのコードを書くのは苦痛になります。単一観測を含むドロップ要因レベル

db0 <- data.frame(let = c(sample(letters[1:5], 99, replace = T),"z"), 
        let2 = sample(letters[6:11], 100, replace = T)) 

#Checking which factor has levels with only one obs 
facLevels <- lapply(db0, table) 
facNames <- list() 
for(i in 1:length(facLevels)){ 
    facNames[i]<-ifelse(min(facLevels[[i]])==1, names(facLevels[i]), NA) 
} 
facNames <- as.character(facNames[!is.na(facNames)]) 

私がしたいことは基本的にはレットにzレベルをドロップすることです。おかげさまで

+2

のために書いて好きではない場合は?データからその行を削除しますか?その値をzではなくNAに設定したいのですか? – MrFlick

+0

はい、その行をnaに設定することは簡単に解決できるので解決策になります。私は多くのレベルの要素がたくさんあることを覚えておいてください。どのレベルに単一の観察が含まれているかは事前に分かりません。そのため、手動で行うよりもむしろこのアプローチを選択しています。 –

答えて

0

ここでループは、1回の観測で任意の因子レベルをNAに設定し、その後、その因子レベルをリファクタリングすることによってその因子レベルをカラムから完全に削除します。

db0 <- data.frame(let = c(sample(letters[1:5], 99, replace = T),"z"), 
    let2 = sample(letters[6:11], 100, replace = T)) 

#Checking which factor has levels with only one obs 
facLevels <- lapply(db0, table) 
# make a list for each factor level that has one value 
to_change <- lapply(facLevels, function(x) names(x)[x==1]) 

for(i in 1:ncol(db0)){ 
    if(length(to_change[[i]])>0){ 
    # set as NA 
    db0[which(db0[,i] %in% to_change[[i]]),i] <- NA 
    # removes the factor level, remove the code below if this is not what 
    # what you wanted to do 
    db0[,i] <- as.factor(db0[,i]) 
    } 
} 

> tail(db0) 
    let let2 
95  b i 
96  a g 
97  c k 
98  d j 
99  d f 
100 <NA> j 

> levels(db0[,i]) 
[1] "f" "g" "h" "i" "j" "k" 
+0

ありがとう、これは私が探していたものです –

0

そして、あなたはあなたが「Zレベルを落とす」ことで、正確に何を意味するのループ

# create a sample dataset 
db0 <- data.frame(let1 = c(sample(letters[1:5], 99, replace = T),"z"), 
        let2 = sample(letters[6:11], 100, replace = T)) 

# calculate how many times each level is present 
facLevel <- lapply(db0, table) 

# drop levels which are present once 
test <- sapply(facLevel, function(x) x[x != 1]) 

# drop rows in the original dataset where a unique level is present (do this for both columns) 
db1 <- db0[rowSums(mapply(function(x, y) x %in% names(y), db0, test)) == ncol(db0), ] 
関連する問題