2017-01-18 2 views
1

Я искал довольно много и не нашел вопроса, который решает эту проблему, но если на это был дан ответ, простите меня, я все еще довольно зеленый, когда дело доходит до кодирования вообще , У меня есть кадр данных с большим количеством переменных, которые я хотел бы объединить. & создавать новые переменные на основе имен, которые я поставил во втором кадре данных в цикле. Кадр данных formulas должны создавать & столбцы вызовов из основного фрейма данных dataВызов и создание новых столбцов на основе строки

USDb = c(1,2,3) 
USDc = c(4,5,6) 
EURb = c(7,8,9) 
EURc = c(10,11,12) 
data = data.frame(USDb, USDc, EURb, EURc) 

Теперь я хотел бы создать новый столбец data$USDa как определено

data$USDa = data$USDb - data$USDc 

и так далее для евро и других переменные. Это достаточно легко сделать вручную, но я хотел бы создать цикл, который вытягивает имена из formulas, что-то вроде этого:

a = c("USDa", "EURa") 
b = c("USDb", "EURb") 
c = c("USDc", "EURc") 
formulas = data.frame(a,b,c) 

for (i in 1:length(formulas[,a])){ 
    data$formulas[i,a] = data$formulas[i,b] - data$formulas[i,c] 
    } 

Очевидно data$formulas[i,a] это возвращает NULL, поэтому я попытался data$paste0(formulas[i,a]) и возвращает Error: attempt to apply non-function

Как я могу заставить эти строки распознаваться как переменные таким образом? Благодарю.

ответ

0

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

x = apply(formulas, 1, function(x) data[[x[3]]] - data[[x[2]]]) 
colnames(x) = formulas$a 
x 
#  USDa EURa 
#[1,] 3 3 
#[2,] 3 3 
#[3,] 3 3 

cbind(data, x) 
# USDb USDc EURb EURc USDa EURa 
#1 1 4 7 10 3 3 
#2 2 5 8 11 3 3 
#3 3 6 9 12 3 3 
+0

да, это решение работало на фактические данные, которые у меня есть, и для меня кажутся более элегантными, чем циклические. Спасибо за руководство. – chrstnsn

1

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

for (i in 1:length(formulas[,"a"])){ 
    data[formulas[i,"a"]] = data[formulas[i,"b"]] - data[formulas[i,"c"]] 
} 
  1. formulas[,a] не будет работать, потому что у вас есть переменная определена как a уже, что не подходит в качестве индекса. Вместо этого используйте formulas[, "a"], если вы хотите, чтобы все строки из столбца «a» в data.frame formulas.
  2. data$formulas буквально ищет колонку под названием «формулы» в data.frame data. Вместо этого вы хотите, чтобы написать data[formulas] (конечно, зная, что вам нужно индексировать formulas для того, чтобы сделать его надлежащую строку)
0

Другим вариантом является split с sapply

sapply(setNames(split.default(as.matrix(formulas[-1]), 
    row(formulas[-1])), formulas$a), function(x) Reduce(`-`, data[rev(x)])) 
#  USDa EURa 
#[1,] 3 3 
#[2,] 3 3 
#[3,] 3 3 
Смежные вопросы