如何按行将DataFrame列值除以多列之和实现列标准化
如何在R中对DataFrame按行实现列值归一化(除以该行总和)
你遇到的问题很典型:之前的代码里sum(df$col1, df$col2, df$col3, df$col4)会把所有列的所有元素加起来得到一个全局总和,而不是你需要的每行单独的总和,所以才得不到预期的0.25结果。下面是几种实用的解决方案:
方法一:基础R实现(无需额外包)
分步实现(清晰直观)
# 先计算每行的总和(只针对col1到col4) row_sums <- rowSums(df[, c("col1", "col2", "col3", "col4")]) # 逐个创建归一化列 df$col1_norm <- df$col1 / row_sums df$col2_norm <- df$col2 / row_sums df$col3_norm <- df$col3 / row_sums df$col4_norm <- df$col4 / row_sums
批量生成归一化列(更简洁)
如果原列很多,手动逐个写太麻烦,可以用apply批量处理:
# 对原列按行执行归一化操作,结果转成数据框 normalized_cols <- as.data.frame( t(apply(df[, 1:4], 1, function(row_values) row_values / sum(row_values))) ) # 给归一化列重命名(原列名+_norm) names(normalized_cols) <- paste0(names(df[,1:4]), "_norm") # 把归一化列合并到原数据框 df <- cbind(df, normalized_cols)
方法二:dplyr/tidyverse风格(更简洁高效)
如果你习惯用tidyverse工具链,用dplyr的across函数可以快速实现:
library(dplyr) df <- df %>% # 计算每行的总和 mutate(row_sum = rowSums(across(col1:col4))) %>% # 对col1到col4批量生成归一化列,自动命名为原列名+_norm mutate(across(col1:col4, ~ .x / row_sum, .names = "{col}_norm")) %>% # 可选:移除临时的row_sum列 select(-row_sum)
如果你的R版本稍旧,也可以用rowwise()的方式:
df <- df %>% rowwise() %>% mutate( row_sum = sum(col1, col2, col3, col4), col1_norm = col1 / row_sum, col2_norm = col2 / row_sum, col3_norm = col3 / row_sum, col4_norm = col4 / row_sum ) %>% ungroup() %>% select(-row_sum)
验证结果
运行上述代码后,你的DataFrame会生成预期的4个归一化列,每行的col1_norm到col4_norm值都是0.25,完全符合你的需求。
内容的提问来源于stack exchange,提问作者wingsoficarus116
相关产品推荐
相关产品推荐

