Tenho um código onde há um cenário ( sc
coluna) e um nome de código ( cd
coluna). Quero calcular a diferença entre todos os cenários para o primeiro (então cenário 2-1
, 3-1
, etc. Tenho vários outros cenários...). Existe uma maneira rápida de codificar qual cenário será comparado, por exemplo, se eu agora o cenário do qual todos os outros são comparados é agora o cenário 2, seria 1-2
, 3-2
, etc.?
Mas também quero ter certeza de que, entre os cenários, eu subtraia apenas os mesmos nomes de código ( cd
), então ( sc1.cd1 - sc2.cd1
), ( sc1.cd2 - sc2.cd2
), etc.
Também quero a diferença percentual entre o sc
cenário 1 em comparação aos outros para cada código.
No momento, meu código assume que, quando comparo os cenários, eles cd
estão na mesma ordem. Haveria uma maneira de comparar os cenários e o código juntos em vez de usar um subconjunto dos dados?
set.seed(123456)
vals = as.vector(mapply(FUN = rpois, n = 10, lambda = c(5, 10, 100)))
df.test = data.frame(cd = rep(1:10,3), sc = rep(1:3, each =10 ), vals)
# New empty column
df.test$delta = NA
# Subset each scenarios and subtract for the first scenario
df.test[df.test$sc ==1,'delta'] = df.test[df.test$sc ==1,'vals']-df.test[df.test$sc ==1,'vals']
df.test[df.test$sc ==2,'delta'] = df.test[df.test$sc ==2,'vals']-df.test[df.test$sc ==1,'vals']
df.test[df.test$sc ==3,'delta'] = df.test[df.test$sc ==3,'vals']-df.test[df.test$sc ==1,'vals']
# Get difference
df.test$diff = abs(abs(df.test$delta) - df.test$vals)
# Calculate percentage
df.test$delta.perc = abs(df.test$delta) / df.test$diff +1
df.test$diff * df.test$delta.perc
# Percentage increase
df.test$delta.perc.increase = df.test$delta.perc *100
Você poderia fazer
sapply
a subtração sobre ounique(sc)
. Usandotransform
você não precisa escreverdf.test$
o tempo todo.Usando
within
, mais conciso, mas as novas colunas são ordenadas de trás para frente.O problema é que você codificou as diferenças entre os cenários, assumindo que
cd
os valores se alinharão perfeitamente, o que torna a alteração do cenário base não tão trabalhosa, mas definitivamente um incômodo.Podemos usar
dplyr
para lidar com o agrupamento e os cálculos, dessa forma podemos definir qualquer cenário base dinamicamente, como1
,2
, ou o que você quiser. Também garantiremos que as diferenças sejam calculadas apenas entrecd
valores correspondentes, para que não haja suposições.dessa forma você pode definir o
base_scenario
para qualquer valor que você quiser e ele atualiza automagicamente, e ao agrupar porcd
nós garantimos que osdelta
's sejam calculados individualmente para cadacd
, então você obtémsc1.cd1 - sc2.cd2
em vez de apenas subtrair linhas em ordem. Eu também adicionei oifelse
para evitardiv/0
erros quando o valor base é0
.Fazer dessa forma permite que você altere o
base_scenario
para qualquer valor e ele será alterado para ele — então você obterá1-2
,3-2
, etc., quando a base for definida como2
.Se eu não expliquei algo bem o suficiente, fique à vontade para deixar uma pergunta nas respostas :)