Я не очень опытный пользователь R, поэтому посоветуйтесь, как оптимизировать то, что я построил и в каком направлении двигаться дальше.
У меня есть один эталонный фрейм данных,он содержит четыре столбца с целочисленными значениями и одним идентификатором.
df <- matrix(ncol=5,nrow = 10)
colnames(df) <- c("A","B","C","D","ID")
# df
for (i in 1:10){
df[i,1:4] <- sample(1:5,4, replace = TRUE)
}
df <- data.frame(df)
df$ID <- make.unique(rep(LETTERS,length.out=10),sep='')
df
A B C D ID
1 2 4 3 5 A
2 5 1 3 5 B
3 3 3 5 3 C
4 4 3 1 5 D
5 2 1 2 5 E
6 5 4 4 5 F
7 4 4 3 3 G
8 2 1 5 5 H
9 4 4 1 3 I
10 4 2 2 2 J
Второй фрейм данных имеет ручной ввод, это пользовательский ввод, позже я хочу превратить его в блестящее приложение, поэтому и прошуоптимизация, потому что мой код не кажется мне очень аккуратным.
df.man <- data.frame(matrix(ncol=5,nrow=1))
colnames(df.man) <- c("A","B","C","D","ID")
df.man$ID <- c("man")
df.man$A <- 4
df.man$B <- 4
df.man$C <- 3
df.man$D <- 4
df.man
A B C D ID
4 4 3 4 man
Я хочу фильтровать строки по ссылке последовательно, следуя правилам:
Если в целом есть точное совпадениестрока между ссылка таблица и руководство , чем извлечь эти (те) из ссылки и показать мне эту строку, если нет, то уменьшите количество соответствующих столбцов справа налево, пока не будет совпадение, ноне менее чем между двумя переменными (столбцы A, B).
Итак, с учетом моих ограниченных знаний, я написал следующее:
# subtraction manual from reference
df <- df %>% dplyr::mutate(Adiff=A-df.man$A)%>%
dplyr::mutate(Bdiff=B-df.man$B)%>%
dplyr::mutate(Cdiff=C-df.man$C) %>%
dplyr::mutate(Ddiff=D-df.man$D)
# check manually how much in a row has zero difference and filter those
ifelse(nrow(df%>%filter(Adiff==0 & Bdiff==0 & Cdiff==0 & Ddiff==0)) != 0,
df0<-df%>%filter(Adiff==0 & Bdiff==0 & Cdiff==0 & Ddiff==0),
ifelse(nrow(df%>%filter(Adiff==0 & Bdiff==0 & Cdiff==0)) != 0,
df0<-df%>%filter(Adiff==0 & Bdiff==0 & Cdiff==0),
ifelse(nrow(df%>%filter(Adiff==0 & Bdiff==0)) != 0,
df0<-df%>%filter(Adiff==0 & Bdiff==0),
"less then two exact match")
))
tbl_df(df0[,1:5])
# A tibble: 1 x 5
A B C D ID
<int> <int> <int> <int> <chr>
1 4 4 3 3 G
Это работает и нашло идентификатор G но выглядит уродливо для меня. Итак, первый вопрос - это какой рекомендуемый способ улучшить это? Есть ли какие-то функции, пакеты или что-то, чего мне не хватает?
Второй вопрос - Я хочу усложнить условие.
Представьте, что у нас есть набор справочных данных.
A B C D ID
2 4 3 5 A
5 1 3 5 B
3 3 5 3 C
4 3 1 5 D
2 1 2 5 E
5 4 4 5 F
4 4 3 3 G
2 1 5 5 H
4 4 1 3 I
4 2 2 2 J
Ручной ввод
A B C D ID
4 4 2 2 man
Правила фильтрации должны быть следующими:
Если существует точное совпадение во всей строке между ссылка table и manual , чем извлечь эти данные из ссылки и показать мне эту строку, если нет, то уменьшить количество совпадающих столбцов справа налево до совпадения, но не между менее чем двумя переменными(столбцы A, B).
Из тех строк, в которых у меня только два совпадения переменных, отфильтруйте те, которые имеют ± 1 разность в столбцах справа. Поэтому я должен был отфильтровать дела G и I из справочной таблицы из приведенного выше примера.
продолжать идти так, как я делалвыше, я бы сделал следующее:
ifelse(nrow(df0%>%filter(Cdiff %in% (-1:1) & Ddiff %in% (-1:1)))>0,
df01 <- df0%>%filter(Cdiff %in% (-1:1) & Ddiff %in% (-1:1)),
ifelse(nrow(df0%>%filter(Cdiff %in% (-1:1)))>0,
df01<- df0%>%filter(Cdiff %in% (-1:1)),
"NA"))
В конце будет около 11 столбцов, но я предполагаю, что это не имеет большого значения.
Помняэта цель - как бы вы предложили продолжить? Спасибо!