2013-05-29 2 views
0

Предположим, я следующий кадр данных:Удаление строк в кадре данных с помощью функции ПОЛУЧИТЬ

mydataframe <- data.frame(ID=c(1,2,NA,4,5,NA),score=11:16) 

Я хочу, чтобы получить следующий кадр данных в конце:

mydataframe[-which(is.na(mydataframe$ID)),] 

мне нужно сделать этот вид (и другие подобные манипуляции) со многими другими кадрами данных. Итак, я решил присвоить имя mydataframe и переменную, представляющую интерес.

dbname <- "mydataframe" 
varname <- "ID" 
attach(get(dbname)) 

У меня есть ошибка в следующей строке, понятно.

get(dbname) <- get(dbname)[-which(is.na(get(varname))),] 
detach(get(dbname)) 

Как это решить? (Я не хочу назначать новый фрейм данных, хотя сейчас это кажется только решением. Я буду использовать «dbname» много раз после этого.) Спасибо заранее.

+8

Egads. Зачем? Зачем ты это делаешь? Я гарантирую, что есть лучший способ. Скорее всего, используя списки. Это всегда сводится к использованию списков ... – Dason

ответ

4

Там нет get<- функции, и нет get(colname) функции (так как COLNAMES не являются объектами первого класса), но есть assign() функции:

assign(dbname, get(dbname)[!is.na(get(dbname)[varname]), ]) 

Вы также не хотите использовать -which(.). Это сработало бы здесь, так как были некоторые соответствия этому условию. Тем не менее, это вас укусит, когда не будет никаких строк, которые соответствуют, и вместо того, чтобы ничего не возвращать, как он должен, он вернет все, начиная с vec[numeric(0)] == vec. Используйте только «which» для «позитивного» выбора.

+0

Мне нравится ваше объяснение относительно 'which'. В любом случае, существует ли какая-либо разница между вашим кодом и myidataframe [! Is.na (mydataframe [varname])], т.е. существуют ли какие-либо преимущества при использовании 'assign'? – fdetsch

+0

Я очень сомневаюсь, что между 'mydataframe <- mydataframe [! Is.na (mydataframe [varname])] и версией' assign' будет большая разница. Я предложил, чтобы версия 'assign' должна была показать, как получить задание с символьным значением для« name », которое оказалось вашей стратегией. Роль функции 'assign' состоит в том, чтобы преобразовать свой первый аргумент, заданный как значение символа, в имя языка R и завершить назначение. –

+0

@DWin Спасибо за ответ. Это то, что я искал. Изучение «get (dbname) [varname]», также очень полезно для меня. Кроме того, спасибо за показ возможной лазейки в "-which (.)". – HBat

1

Я могу полностью понять вашу потребность в этом, так как мне также часто нужно перебирать набор кадров данных. Я считаю, следующий код должен помочь вам:

mydataframe <- data.frame(ID=c(1,2,NA,4,5,NA),score=11:16) 

#define target dataframe and varname 
dbname <- "mydataframe" 
varname <- "ID" 

tmp.df <- get(dbname) #get df and give it a temporary name 
col.focus <- which(colnames(tmp.df) == varname) #define the column of focus 
tmp.df <- tmp.df[which(!is.na(tmp.df[,col.focus])),] #cut out the subset of the df where the column of focus is not NA. 

#Result 
    ID score 
1 1 11 
2 2 12 
4 4 14 
5 5 15 
4

Как предлагает @Dason, для такого рода работ создаются списки.

т.д .:

# make a list with all your data.frames in it 
# (just repeating the one data.frame 3x for this example) 
alldfs <- list(mydataframe,mydataframe,mydataframe) 

# apply your function to all the data.frames in the list 
# have replaced original function in line with @DWin and @flodel's comments 
# pointing out issues with using -which(...) 
lapply(alldfs, function(x) x[!is.na(x$ID),]) 
+1

+1, но, пожалуйста, прочитайте комментарий @ DWin о том, что вы не используете '-which' и не исправляете свой код. Другим элегантным способом здесь является 'lapply (alldfs, subset,! Is.na (ID))'. – flodel

+0

@flodel - хорошая точка, я даже не оценил используемую функцию, когда я ударил ее в 'lapply'. Отредактировано сейчас. – thelatemail

2

Предложение использовать список фреймов данных хорошо, но я думаю, что люди при условии, что вы находитесь в ситуации, когда все кадры данных загружаются одновременно. Возможно, это не обязательно, например, если вы работаете над несколькими проектами и просто хотите, чтобы какой-либо шаблонный код использовался во всех них.

Что-то вроде этого должно соответствовать счету.

stripNAs <- function(df, var) df[!is.na(df[[var]]), ] 

mydataframe <- stripNAs(mydataframe, "ID") 
cars <- stripNAs(cars, "speed") 
+0

Когда я попробовал это, он дал мне следующую ошибку: Ошибка в df [[var]]: индекс за пределами – HBat

+0

Должен быть 'mydataframe <- stripNAs (mydataframe,« ID »)' – Aaron

+0

@Aaron благодарит за то, что поймал это, исправлено. –

Смежные вопросы