I have a dataframe that looks as follows:
id amount number discount
1 400 10 0.7
2 500 5 0.7
3 600 10 0.6
df <- structure(list(id = 1:3, amount = c(400L, 500L, 600L), number = c(10L,
5L, 10L), discount = c(0.7, 0.7, 0.6)), class = "data.frame", row.names = c(NA,
-3L))
I have a formula, where N is the number column in the dataframe
So for the first row I would be summing:
400/(1+0.7)^0 + 400/(1+0.7)^1 + 400/(1+0.7)^2 +.... + 400/(1+0.7)^9
How could I do this for each row?
Is this matches your desired output?
mapply(function(x, y, z) sum(Reduce(function(.x, .y) {.x/y }, seq_len(z -1), x, accumulate = T)),
df$amount, 1 + df$discount, df$number)
[1] 966.610 1128.764 1585.448
df <- structure(list(id = 1:3, amount = c(400L, 500L, 600L), number = c(10L,
5L, 10L), discount = c(0.7, 0.7, 0.6)), class = "data.frame", row.names = c(NA,
-3L))
library(tidyverse)
df %>% rowwise() %>%
mutate(calc = sum(accumulate(seq_len(number-1), .init = amount, ~ .x/(1 + discount))))
#> # A tibble: 3 x 5
#> # Rowwise:
#> id amount number discount calc
#> <int> <int> <int> <dbl> <dbl>
#> 1 1 400 10 0.7 967.
#> 2 2 500 5 0.7 1129.
#> 3 3 600 10 0.6 1585.
Created on 2021-05-24 by the reprex package (v2.0.0)
accumulate
creates a geometrical series as output
accumulate(1:9, .init = 400, ~.x/(1 + 0.7))
[1] 400.000000 235.294118 138.408304 81.416650 47.892147 28.171851 16.571677 9.748045 5.734144 3.373026
Using rowwise
and sum
will SUM the geometrical series, as finally desired
sum(accumulate(1:9, .init = 400, ~.x/(1 + 0.7)))
[1] 966.61
You can use any of the apply command in base R -
mapply(function(x, y, z) sum(x/(y ^ 0:z)), df$amount, 1 + df$discount, df$number)
OR with dplyr
-
library(dplyr)
df %>%
rowwise() %>%
mutate(res = sum(amount/((1 + discount) ^ 0:number))) %>%
ungroup
# id amount number discount res
# <int> <int> <int> <dbl> <dbl>
#1 1 400 10 0.7 1172.
#2 2 500 5 0.7 1142.
#3 3 600 10 0.6 1757.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With