Это глупо, но работает.
Например, я создам описанный вами кадр данных:
selection <- c('sel1','sel2')
weight <- c(0.4,0.5)
df <- data.frame(selection = selection,weight = weight)
Для начала убедитесь, что переменная selection
Тип character
, а не factor
.
df$selection <- as.character(df$selection)
Чтобы создать список имен для нового кадра данных, мы создадим правильные строки и вставим в индексы.
indices <- sort(c(1:nrow(df),1:nrow(df)))
tags <- c(rbind(rep(names(df)[1],nrow(df)),rep(names(df)[2],nrow(df))))
new_names <- sapply(1:(2*nrow(df)),function(j) paste(tags[j],indices[j],sep="_"))
А вот и клумая часть, написанная как функция.Давайте пройдемся по очереди и добавим новые переменные в пустой фрейм данных.
make_new_df <- function(df) {
new_df <- data.frame()
for (i in (1:length(new_names))) {
test <- i %% ncol(df)
if (test == 0) {
row_index <- floor(i/ncol(df))
col_index <- ncol(df)
} else {
row_index <- floor(i/ncol(df))+1
col_index <- (i %% ncol(df))
}
new_df[1,new_names[i]] <- df[row_index,col_index]
}
return(new_df)
}
Давайте проверим, работает ли это для вашего примера:
> make_new_df(df)
selection_1 weight_1 selection_2 weight_2
1 sel1 0.4 sel2 0.5
Будет работать функция make_new_df
для входного кадра данных df
с любым количеством строк и столбцов, но для него требуется правильная конфигурация для new_names
.Предварительное построение кода new_names
будет работать для любого количества строк, но только для двух столбцов (таким образом, оно находится за пределами функции).Например, код
selection <- c('sel1','sel2','sel3','sel4')
weight <- c(0.4,0.5,0.6,0.7)
df <- data.frame(selection = selection,weight = weight)
indices <- sort(c(1:nrow(df),1:nrow(df)))
tags <- c(rbind(rep(names(df)[1],nrow(df)),rep(names(df)[2],nrow(df))))
new_names <- sapply(1:(2*nrow(df)),function(j) paste(tags[j],indices[j],sep="_"))
make_new_df(df)
выдает
selection_1 weight_1 selection_2 weight_2 selection_3 weight_3 selection_4 weight_4
1 sel1 0.4 sel2 0.5 sel3 0.6 sel4 0.7