Я хотел бы найти разумный метод для обнаружения и выбора «принципиальных» текстовых столбцов данных из моих data.frames.
В этих столбцах содержатся открытые ответы на опросы, поэтому они содержат разнородные строки, состоящие в основном из буквенных символов. В идеале этот метод
- удаляет все множители, цифры c, дату и логические столбцы
- удаляет малонаселенные текстовые столбцы
- удаляет текстовые столбцы с несколькими уникальные элементы
- смогут работать с нестандартными символами
Вот оригинальный пример того, чего я хотел бы достичь:
Оригинал входные данные
v1 v2 v3 v4 v5 v6 v7 v8 v9 v10 v11 v12 v13 v14
1 Na Gu Rx Ll bird a a 1 88,626 1 1 ç a TRUE
2 Ue Ho Iy <NA> bird b b 2 48,666 2 2 é b FALSE
3 Vk Lv <NA> <NA> bird a c 3 12,559 3 1 ë ç TRUE
4 Pd Hk <NA> <NA> bird b d 4 3,794 4 2 õ d FALSE
5 Ay Nd <NA> <NA> <NA> a e 5 75,239 5 1 ï é TRUE
6 Xj <NA> <NA> <NA> <NA> b a 6 44,559 6 2 í f FALSE
7 Zn <NA> <NA> <NA> <NA> a b 7 21,100 7 1 ð g TRUE
8 Mw <NA> <NA> <NA> <NA> b c 8 7,790 8 2 ø h FALSE
9 Yx <NA> <NA> <NA> <NA> a d 9 84,470 9 1 ö i TRUE
10 Oj <NA> <NA> <NA> <NA> b e 10 45,724 10 2 ò j FALSE
Исходный желаемый вывод (с ошибками, см. Обновление ниже)
v1 v2 v7 v12 v13
1 Na Gu a c a
2 Ue Ho b e b
3 Vk Lv c e c
4 Pd Hk d o d
5 Ay Nd e i e
6 Xj <NA> a i f
7 Zn <NA> b d g
8 Mw <NA> c o h
9 Yx <NA> d o i
10 Oj <NA> e o j
Вот код для исходных входных данных:
# made-up data
df <- data.frame(stringsAsFactors = F,
v1 = paste0(sample(LETTERS, 10, replace = T), sample(letters, 10, replace = T)),
v2 = c(paste0(sample(LETTERS, 5, replace = T), sample(letters, 5, replace = T)), rep(NA, 5)),
v3 = c(paste0(sample(LETTERS, 2, replace = T), sample(letters, 2, replace = T)), rep(NA, 8)),
v4 = c(paste0(sample(LETTERS, 1, replace = T), sample(letters, 1, replace = T)), rep(NA, 9)),
v5 = c(rep("bird", 4), rep(NA, 6)),
v6 = factor(rep(c("a", "b"), 5)),
v7 = rep(c("a", "b", "c", "d", "e"),2),
v8 = 1:10,
v9 = paste0(sample(1:99, 10, replace =T), ",", sample(1:999, 10, replace =T)),
v10 = as.character(1:10),
v11 = factor(rep(c(1, 2), 5)),
v12 = c('ç','é','ë','õ','ï','í','ð','ø','ö','ò'),
v13 = c('a','b', 'ç','d',' é',letters[6:10]),
v14 = as.logical(rep(c("TRUE", "FALSE"), 5)))
До сих пор я был в состоянии выделить векторы символов
df <- df[, sapply(df, is.character)]
и преобразовать все символы в Latin_ASCII, чтобы заменить нестандартные буквы
df[] <- lapply(df, stringi::stri_trans_general, "Latin-ASCII")
Но я пытаюсь найти разумное / надежное решение для удаления малонаселенных (например, v3 и v4), высокоповторных (например, v5) или потенциальных чисел c, отформатированных в виде символов (например, v9 и v10). ). Какой хороший подход?
Обновление
Получив полезный ответ и комментарий от @Matias Andina, я пришел к выводу, что мои исходные входные данные были ошибочными, потому что 10 строк данных было недостаточно, чтобы правильно отразить мою цель удаления текстовых столбцов с «несколькими уникальными элементами». Итак, вот второй пример, показывающий первые двадцать строк для ввода и желаемого вывода. В соответствии с моим первоначальным вопросом, описанным в начале этого поста, цель состоит в том, чтобы отбросить все столбцы «d» и сохранить столбцы «k». Матиас заслуживает похвалы, за его ответ уже обращается d3-d9.
Дополнительные входные данные
k1 k2 k3 d1 d2 d3 d4 d5 d6 d7 d8 d9
Ze E,w h,Y c bird 12,36 b 38 38 2 FALSE 18/03/2020
Gr Y,y w,J d NA 88,510 b 54 54 2 FALSE 3/04/2020
Ze J,x w,G e bird 26,932 b 30 30 2 FALSE 10/03/2020
Nt V,u a,A d bird 8,660 a 19 19 1 TRUE 28/02/2020
Bn W,l z,O c bird 19,684 a 3 3 1 TRUE 12/02/2020
Km L,c h,d a bird 8,649 b 16 16 2 FALSE 25/02/2020
Lx N,e s,H d NA 92,838 b 84 84 2 FALSE 3/05/2020
Vv R,s m,b e bird 58,793 b 40 40 2 FALSE 20/03/2020
El A,h i,E d bird 61,589 b 44 44 2 FALSE 24/03/2020
Az B,b n,é c NA 45,11 b 58 58 2 FALSE 7/04/2020
Tq J,y w,N b NA 81,288 b 82 82 2 FALSE 1/05/2020
Lg Z,l h,I c NA 17,418 b 88 88 2 FALSE 7/05/2020
Oh F,b e,Q a NA 28,887 a 71 71 1 TRUE 20/04/2020
Rj I,f ç,F b NA 59,213 a 97 97 1 TRUE 16/05/2020
Pw X,u n,Z b bird 51,622 b 42 42 2 FALSE 22/03/2020
Dv A,d l,X c bird 29,148 b 18 18 2 FALSE 27/02/2020
Hp C,o w,Z d bird 78,737 b 24 24 2 FALSE 4/03/2020
Br D,i b,a e NA 35,231 a 65 65 1 TRUE 14/04/2020
Re X,g b,O b NA 18,244 b 92 92 2 FALSE 11/05/2020
Исправлено желаемое значение
k1 k2 k3
Ze E,w h,Y
Gr Y,y w,J
Ze J,x w,G
Nt V,u a,A
Bn W,l z,O
Km L,c h,d
Lx N,e s,H
Vv R,s m,b
El A,h i,E
Az B,b n,é
Tq J,y w,N
Lg Z,l h,I
Oh F,b e,Q
Rj I,f ç,F
Pw X,u n,Z
Dv A,d l,X
Hp C,o w,Z
Br D,i b,a
Re X,g b,O
Вот код для дополнительных входных данных:
set.seed(8)
df <- data.frame(stringsAsFactors = F,
k1 = paste0(sample(LETTERS, 100, replace = T), sample(letters, 100, replace = T)),
k2 = paste0(sample(LETTERS, 100, replace = T), ",", sample(letters, 100, replace = T)),
k3 = paste0(sample(c('a','b', 'ç','d',' é',letters), 100, replace = T), ",",
sample(c('a','b', 'ç','d',' é', LETTERS), 100, replace = T)),
d1 = rep(c("a", "b", "c", "d", "e"),20),
d2 = c(rep("bird", 51), rep(NA, 49)),
d3 = paste0(sample(1:99, 100, replace =T), ",", sample(1:999, 100, replace =T)),
d4 = factor(rep(c("a", "b"), 50)),
d5 = 1:100,
d6 = as.character(1:100),
d7 = factor(rep(c(1, 2), 10)),
d8 = as.logical(rep(c("TRUE", "FALSE"), 50)),
d9 = seq(from = as.Date("2020-02-10"), to = as.Date("2020-02-10") + 99, by = 'day'))
df <- df[sample(nrow(df)),]