You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何仅对指定行做宽表转换并添加对应年度总计列?

按年份添加总计列并过滤指定行的解决方案

样本数据

indcode <- c(71,72,81,82,99,000000,71,72,81,82,99,000000)
year <- c(2020,2020,2020,2020,2020,2020,2021,2021,2021,2021,2021,2021)
employment <- c(3,5,7,9,2,26,4,6,8,10,3,31)

test <- data.frame(indcode, year, employment)

需求说明

给上述test数据框新增total列,total的值为对应年份中indcode等于000000的employment数值,同时删除所有indcode为000000的行。尝试用pivot_wider方法但无法让总计值重复到每行,期望结果如下:

year indcode employment total
1 2020      71          3    26
2 2020      72          5    26
3 2020      81          7    26
4 2020      82          9    26
5 2020      99          2    26
6 2021      71          4    31
...

解决方案

方法一:结合pivot_wider与pivot_longer实现

利用tidyverse包的函数,先将总计值转为单独列,再转回长格式并过滤:

library(tidyverse)

result <- test %>%
  # 按年份拆分,将不同indcode转为列,employment为对应值
  pivot_wider(
    id_cols = year,
    names_from = indcode,
    values_from = employment,
    names_prefix = "ind_",
    values_fill = 0
  ) %>%
  # 将原000000对应的列重命名为total(原数据中000000会被转成整数0)
  rename(total = ind_0) %>%
  # 转回长格式,恢复indcode和employment列
  pivot_longer(
    cols = starts_with("ind_"),
    names_to = "indcode",
    values_to = "employment",
    names_prefix = "ind_"
  ) %>%
  # 过滤掉indcode为0的行
  filter(indcode != "0") %>%
  # 将indcode转回整数类型
  mutate(indcode = as.integer(indcode)) %>%
  # 调整列顺序并按年份、行业代码排序
  select(year, indcode, employment, total) %>%
  arrange(year, indcode)

print(result)

方法二:提取总计数据后左连接(更简洁)

先提取各年份的总计值,再通过左连接将总计值匹配到对应年份的每行数据:

library(dplyr)

# 提取各年份的总计值,存储为单独数据框
total_data <- test %>%
  filter(indcode == 0) %>% # 原数据中000000会被自动转为整数0
  select(year, total = employment)

# 过滤掉原数据中的总计行,再左连接总计数据
result <- test %>%
  filter(indcode != 0) %>%
  left_join(total_data, by = "year") %>%
  select(year, indcode, employment, total)

print(result)

注意事项

如果需要保留indcode的字符串格式(比如保留000000而非转为整数0),创建数据框时要指定indcode为字符型:

test <- data.frame(
  indcode = as.character(c(71,72,81,82,99,"000000",71,72,81,82,99,"000000")),
  year = c(2020,2020,2020,2020,2020,2020,2021,2021,2021,2021,2021,2021),
  employment = c(3,5,7,9,2,26,4,6,8,10,3,31)
)

此时对应的过滤和匹配要使用字符串"000000":

total_data <- test %>%
  filter(indcode == "000000") %>%
  select(year, total = employment)

result <- test %>%
  filter(indcode != "000000") %>%
  left_join(total_data, by = "year") %>%
  select(year, indcode, employment, total)

内容的提问来源于stack exchange,提问作者Tim Wilcox

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 20:20:03