下面有一组数据,这些数据显示了虚构的汽车经销店中的许多汽车。 “ current_price”变量显然是汽车当前设定的销售价格。 “ minimum_price”变量显示了在任何情况下汽车都不得出售的硬底价。 (可以假定为购买价格。)
我正在尝试创建一个函数,用户可以在数据库中选择一部分汽车(使用如下所述的“用户定义参数”),然后将“ Current_Price”减少或增加一个百分比或英镑(£)值。
“最低利润参数”设置了所有汽车的最低利润。在此示例中,它们已设置为10英镑和10%。这意味着每辆车的利润必须是10英镑,或者是当前价格的10%(以较高者为准)。
价格变化参数可设置价格变动的幅度以及价格应该上涨还是下跌。
# Dummy data
Type <- rep(c("Car", "Van"),each=3)
Age <- as.numeric(c(2, 2, 5, 4, 8,1))
Colour <- c("Red", "Red", "Yellow", "Red", "Black", "Red")
Make <- c("Ford", "VW", "VW", "VW", "BMW", "Ford")
Current_Price <- as.numeric(c(1050, 1000, 1500, 995, 2200, 2100))
Minimum_Price <- as.numeric(c(900, 600, 500, 850, 1900, 1950))
df1 <- data.frame(Type, Age, Colour, Make, Current_Price, Minimum_Price)
# User defined parameters - price to be changed for all cars which fit below selection
Input_Type <- "Car"
Input_Min_Age <- 2 # All cars this age and above
Input_Max_Age <- 10 # All cars this age and below
Input_Colour <- "Red"
Input_Make <- c("Ford", "VW")
# Minimum profit parameters
Input_Min_Pounds <- 10
Input_Min_Percentage <- 0.10
# Price change parameters
Input_Change_Type <- "Percentage" # "Percentage" or "Pound"
Input_Change_Value <- -0.10 # "-" sign to represent price reduction
鉴于上述情况,我希望第1行和第2行会受到更改的影响。 1号线的价格应从1,050英镑下调至1,000英镑。这是因为,当价格的10%为利润(900 /(1-0.10)= 1000)时,£1,000是可能的最低价格。
2号线的价格应该简单地下降10%至900。
有没有人知道如何将其放入对于不习惯使用R的人来说非常直观的功能?
答案 0 :(得分:1)
此答案使用data.table
来支持原始“ data.frame”中的价格变化(如您对问题的评论中所述),解决方案可能如下所示
我仍然忽略定价逻辑,因为我想专注于可用性方面 (这种专门的定价逻辑是武断的,对于SO的其他任何人来说都不是特别感兴趣;如果您有自己实施的特定问题,请提出一个新问题并详细解释该问题。)
library(data.table)
data <- as.data.table(df1)
calc_price <- function(Current_Price,
Minimum_Price,
price_change_type,
price_change_value,
min_profit_pounds,
min_profit_percentage) {
# TODO implement your pricing logic here...
return(Current_Price + 1)
}
update_car_prices <- function(data,
filter,
price_change_type = c("Percentage", "Pound"),
price_change_value = 0,
min_profit_pounds = 10,
min_profit_percentage = 0.10) {
stopifnot(is.data.table(data))
price_change_type <- match.arg(price_change_type) # use the first value if none was provided
filter_exp <- substitute(filter) # "parse" the passed value as expression
# date the price using a separate function to encapsulate the logic
data[eval(filter_exp), Current_Price := calc_price(Current_Price,
Minimum_Price,
price_change_type,
price_change_value,
min_profit_pounds,
min_profit_percentage)][]
return(data)
}
用法仍然类似于我的data.frame
答案,例如g。:
update_car_prices(data, Type == "Car" & Age >= 2 & Age <= 10 & Colour == "Red" & Make %in% c("Ford", "VW"))
update_car_prices(data, Colour == "Red")
update_car_prices(data, Colour == "Red", "Pound", 500)
区别是:
data.table
(data
)来查看影响data
通过引用传递以来,原始data.table
已更改
并且我正在使用data.table语法:=
答案 1 :(得分:0)
此答案基于data.frame
...
您的问题涉及多个方面(定价逻辑,过滤逻辑和可用性)。
我将重点放在可用性上(并忽略定价逻辑,因为这只是一个故意的细节)。
我至少看到三个选项:
使用强类型函数:
get_car_prices1 <- function(data, Input_Type, Input_Min_Age, Input_Max_Age, Input_Colour, Input_Make, Input_Min_Pounds, Input_Min_Percentage)
通过...
使用带有故意数量的参数的“无类型”函数通过仅传递所需的参数来支持过滤:
get_car_prices2 <- function(data, Input_Min_Pounds, Input_Min_Percentage, ...)
通过substitute
+ eval
我决定将选项3设置为最佳(用户友好+灵活)选项恕我直言:
get_car_prices <- function(data,
filter,
price_change_type = c("Percentage", "Pound"),
price_change_value = 1)
{
price_change_type <- match.arg(price_change_type) # use the first value if none was provided
filter_exp <- substitute(filter) # "parse" the passed value as expression
data_subset <- subset(data, eval(filter_exp))
# TODO add your pricing logic here (e. g. using "ifelse")
return(data_subset)
}
# Usage examples:
get_car_prices(df1, Colour == "Red")
# Type Age Colour Make Current_Price Minimum_Price
# 1 Car 2 Red Ford 1050 900
# 2 Car 2 Red VW 1000 600
# 4 Van 4 Red VW 995 850
# 6 Van 1 Red Ford 2100 1950
get_car_prices(df1, Type == "Car" & Age >= 2 & Age <= 10 & Colour == "Red" & Make %in% c("Ford", "VW"))
# Type Age Colour Make Current_Price Minimum_Price
# 1 Car 2 Red Ford 1050 900
# 2 Car 2 Red VW 1000 600
get_car_prices(df1, Colour == "Red", "Pound", 500)
# ...
get_car_prices(df1, Colour == "Red", "dumping price", 1)
# Error in match.arg(price_change_type) :
# 'arg' should be one of “Percentage”, “Pound”
# But: The user has to learn at least the expression logic of R and that variables (and values) are case-sensitive:
get_car_prices(df1, Colour == "red")
# [1] Type Age Colour Make Current_Price Minimum_Price
# <0 rows> (or 0-length row.names)
# Error: Assignment operator (=) used instead of comparison operator (==)
get_car_prices(df1, Colour = "Red")
# Error in get_car_prices(df1, Colour = "Red") :
# unused argument (Colour = "Red")