Замените все значения, которые отличаются от значения NA

Кажется, я наткнулся на затруднительное положение в своих попытках научиться использовать R. У меня есть набор данных, который выглядит так:

col1  /   col2  /   col3   

NA  / 1 /  2

1  /  NA  /2

Что мне нужно сделать, это заменить все, что НЕ NA другим значением (см. ниже)

Col1  /  col2  /    col 3

NA / Data / Data

Data / NA/ Data

Я искал везде в Интернете, кажется, что все хотят заменить NA другими значениями, с другой стороны, мне нужно прямо противоположное, но я не смог найти ни одной команды. Я даже просмотрел «ЕСЛИ», но смог найти только функции, которые заменяют значения, если они либо <, либо =, либо > до определенного числа. Мне нужно что-то, что укажет..."ЕСЛИ отличается от NA, то замените на...."


person David Rogers    schedule 15.11.2012    source источник


Ответы (1)


Данные:

dat <- data.frame(col1 = c(NA, 1), col2 = c(1, NA), col3 = c(2, 2))

Чтобы выбрать все значения, которые не NA, используйте логический оператор ! ("не") вместе с is.na:

dat[!is.na(dat)] <- "Data"

  col1 col2 col3
1 <NA> Data Data
2 Data <NA> Data

То же самое можно сделать и с помощью функции replace:

replace(dat, !is.na(dat), "Data")

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

replace(data.frame(lapply(dat, as.character), stringsAsFactors = FALSE),
        !is.na(dat), "Data")
person Sven Hohenstein    schedule 15.11.2012
comment
Единственная проблема с этим подходом заключается в том, что он делает полную копию объекта того же размера, что и данные. - person mnel; 15.11.2012
comment
@mnel не совсем, !is.na(dat) приводит к логической матрице, которая является меньшим объектом, чем исходный фрейм данных. object.size(dat) приводит к 568 байтам и object.size(!is.na(dat)) к 368 байтам. Тоже, наверное, ничем не поможешь. Если объект настолько велик, что это вызовет проблемы с памятью, то выполнение его по ячейке (например, с двумя циклами), вероятно, будет невыносимо медленным. - person Sacha Epskamp; 15.11.2012
comment
К сожалению, ни одно из предложений не работает для меня. dat ‹- data.frame(col1 = c(NA, 1), col2 = c(1, NA), col3 = c(2, 2)) Приведенное выше я не могу использовать, потому что то, что я назвал в своем примере как 1, 2, в моем реальном фрейме данных я могу иметь даже 1 миллион уникальных значений. dat[!is.na(dat)] ‹- Data Это дает мне эту ошибку, и кажется, что для всех значений в кадре данных генерируются NA replace(dat, !is.na(dat), Data) Это дает мне ту же ошибку, что и выше. Думаю, мне придется продолжать искать Дэвида - person David Rogers; 15.11.2012
comment
Также я забыл упомянуть, что мои данные состоят не из факторов, а из уникальных категориальных значений. В любом случае, большое спасибо. Всего наилучшего. Дэйвид - person David Rogers; 15.11.2012
comment
Дэвид, я думаю, ты упускаешь суть. Учитывая вашу матрицу dat и некоторый другой массив значений для вставки в dat, выражение dat[!is.na(dat)] <- Data подойдет. Если у вас возникли проблемы с массивом Data, опубликуйте полезный образец и сообщите нам, какие элементы (числовые, факторные и т. д.) заполняют этот массив. - person Carl Witthoft; 15.11.2012
comment
Ok. Ну, я не знаю, как поделиться изображением, чтобы вы могли увидеть мой фрейм данных, поэтому вместо этого я опишу его. В первом столбце у меня есть аббревиатура страны (GB, US, CA, IT). Во втором столбце у меня есть почтовый индекс или почтовый индекс (N1, SW10). В третьем столбце у меня есть источник, откуда пришел пользователь, в формате ULR (googleclick... ), но и в этом третьем столбце не все ячейки имеют URL. В некоторых ячейках есть NA, что означает, что пользователь пришел на мою страницу вирусным путем. Я хочу заменить ТОЛЬКО в столбце № 3 все, что не NA, на что-то другое. Имеет ли это смысл? - person David Rogers; 15.11.2012
comment
replace(data.frame(lapply(dat, as.character), stringsAsFactors = FALSE), !is.na(dat), Data) Кажется, это работает нормально, за исключением того, что он заменяет ВСЕ, все столбцы на NA. Можно ли использовать эту функцию, но поставить условие для изменения только определенного столбца? - person David Rogers; 15.11.2012
comment
@DavidRogers Чтобы заменить все значения, отличные от NA, в третьем столбце фрейма данных, используйте эту команду: dat[3] <- as.character(dat[[3]]); dat[!is.na(dat[3]), 3] <- "Data" - person Sven Hohenstein; 15.11.2012
comment
Спасибо, Свен, но мне это не подходит. В вашей функции, когда вы говорите 3, это означает имя столбца или индекс столбца? Это дает мне ошибку, когда я заменяю 3 именем столбца, говоря, что он не находит столбец, хотя он существует. Это формула, которую я использовал file4 ‹- file1[Source] ‹- as.character(file1[[Source]]); файл1[!is.na(файл1[Источник]), Источник] ‹- Данные. И это ошибка, которую он дал мне Ошибка в (функция (x, i, точно) если (is.matrix (i)) as.matrix (x) [[i]] else .subset2 (x,: объект «Источник» не найдено. Хотя столбец существует. - person David Rogers; 15.11.2012
comment
@DavidRogers В моем примере 3 был индексом третьего столбца. Если вы хотите использовать имя столбца (Source), вы должны поместить его в кавычки ("Source"). - person Sven Hohenstein; 15.11.2012
comment
Большое спасибо, Свен, что решил это. Я новичок в R. Еще раз большое спасибо. Всего наилучшего Давид - person David Rogers; 15.11.2012