【问题标题】:Update observations in dataframe according to other dataframe?根据其他数据框更新数据框中的观察结果?
【发布时间】:2018-04-26 07:43:52
【问题描述】:

我有一个数据框说 prod_score:

product score
a       1
d       2
ff      2
e       3
fvf     1

我有另一个具有相同产品的数据框 prod_rank + 他们的排名 prod_rank:

product   rank
a         11
d         4
ff        1
e         5
fvf       9

为了澄清我有很多观察结果,这就是我展示示例数据的原因。

过滤所有得分为 2 的产品:

library(dplyr)
prod_scr_2 <- prod_score %>% filter(score == 2)

现在我想拿prod_scr_2个产品,根据prod_rank df更新分数:

我用过join:

decision_tbl <- inner_join(prod_scr_2, prod_rank, by = "product") %>%
                                                top_n(2,desc(rank))

现在我正在接受decision_tbl$product 并且只想更新获得最高排名的产品的分数。

我使用 match 来做到这一点:

prods2update_idx <- match(decision_tbl$product, prod_score$product)

鉴于我正在尝试更新 prod_score 数据框的匹配索引,请告知我该怎么做?

【问题讨论】:

  • 那么,在这种情况下,哪些是排名靠前的产品?当ff 排名第 1 时,它是否只有产品 d 排名第 4?
  • 排名越低越好。

标签: r join dataframe match


【解决方案1】:

假设感兴趣的分数是 2(如您在示例中提到的),并且排名靠前的产品的更新分数是 100。这些可以更改。

这是一个dplyr 解决方案,因为我看到你开始使用这个包:

library(dplyr)

prod_score = read.table(text = "
product score
a       1
d       2
ff      2
e       3
fvf     1
", header = T, stringsAsFactors = F)

prod_rank = read.table(text = "
product   rank
a         11
d         4
ff        1
e         5
fvf       9
", header = T, stringsAsFactors = F)


prod_score %>% 
  filter(score == 2) %>%                                 # select products with score = 2
  inner_join(prod_rank, by = "product") %>%              # join to get ranks
  filter(rank == max(rank)) %>%                          # keep product(s) with maximum ranks
  rename(given_score = score) %>%                        # change column name (for the next join)
  right_join(prod_score, by = "product") %>%             # join to get scores
  mutate(score = ifelse(!is.na(rank), 100, score)) %>%   # update score when there's a rank value
  select(-given_score, -rank)                            # remove unnecessary columns

#   product score
# 1       a     1
# 2       d   100
# 3      ff     2
# 4       e     3
# 5     fvf     1

在基础 R 中还有一种替代方法。请记住重新构建初始示例数据集:

# get products with score = 2
prod_score$product[prod_score$score == 2] -> prds_score_2

# get ranks for those products
prod_rank[prod_rank$product %in% prds_score_2,] -> prds_score_2_ranks

# keep products with maximum rank to update
prds_score_2_ranks$product[prds_score_2_ranks$rank == max(prds_score_2_ranks$rank)] -> prds_to_update

# update values for those products in your initial table
prod_score$score[prod_score$product %in% prds_to_update] = 100

# see the updates
prod_score

#   product score
# 1       a     1
# 2       d   100
# 3      ff     2
# 4       e     3
# 5     fvf     1

【讨论】:

  • 非常感谢,上面的 dplyr 解决方案几乎就是我用过的解决方案 :)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-03-26
  • 1970-01-01
  • 2020-02-18
  • 2019-05-02
相关资源
最近更新 更多