如何在R中编写符合“optimum is better”准则的归一化函数
R实现“最优区间最佳”准则的归一化函数
要实现的“optimum is better”归一化效果如下图:
实现逻辑
- 保留原有
More is better(越多越好)、Less is better(越少越好)的计算逻辑 - 新增
Optimum is better(最优区间最佳)的分支,新增opt_range参数传入最优区间的上下限 - 分三段计算归一化值:
- 数值低于最优区间下限:按“越多越好”逻辑,将
[x最小值, 最优区间下限]映射到[0, 1] - 数值处于最优区间范围内:直接返回归一化值1
- 数值高于最优区间上限:按“越少越好”逻辑,将
[最优区间上限, x最大值]映射到[1, 0]
- 数值低于最优区间下限:按“越多越好”逻辑,将
完整代码
normalize <- function(x, na.rm = TRUE, relation, opt_range = NULL) { # 入参合法性校验 if (relation == "Optimum is better") { if (is.null(opt_range) || length(opt_range) != 2 || !is.numeric(opt_range)) { stop("使用最优区间模式时,请传入长度为2的数值型参数opt_range,格式为c(区间下限, 区间上限)") } opt_low <- min(opt_range) opt_high <- max(opt_range) } # 计算全局极值 x_min <- min(x, na.rm = na.rm) x_max <- max(x, na.rm = na.rm) # 按不同准则计算归一化值 if (relation == "More is better") { res <- (x - x_min) / (x_max - x_min) } else if (relation == "Less is better") { res <- 1 - (x - x_min) / (x_max - x_min) } else if (relation == "Optimum is better") { # 无依赖版本,使用base R的ifelse实现 res <- ifelse( x <= opt_low, (x - x_min) / (opt_low - x_min), ifelse( x >= opt_high, 1 - (x - opt_high) / (x_max - opt_high), 1 ) ) # 如果已安装dplyr,也可以用更易读的case_when实现: # res <- dplyr::case_when( # x <= opt_low ~ (x - x_min)/(opt_low - x_min), # x >= opt_high ~ 1 - (x - opt_high)/(x_max - opt_high), # TRUE ~ 1 # ) } else { stop("relation参数仅支持'More is better'/'Less is better'/'Optimum is better'三种取值") } return(res) }
测试调用
使用示例数据测试:
set.seed(123) value <- runif(50, min=3, max=8.5) # 调用最优区间模式,最优区间设为6.5-7.5 normalized_res <- normalize( x = value, na.rm = TRUE, relation = "Optimum is better", opt_range = c(6.5, 7.5) ) # 查看原始值和归一化结果对应关系 head(data.frame(原始值 = value, 归一化值 = normalized_res), 10)
内容的提问来源于stack exchange,提问作者UseR10085
相关产品推荐
相关产品推荐

