如何编写 R 函数来查找数据框中的特定条件

Posted

技术标签:

【中文标题】如何编写 R 函数来查找数据框中的特定条件【英文标题】:How to write R function to find a specific condition in a dataframe 【发布时间】:2017-09-08 14:10:01 【问题描述】:

我有一个特定的问题,我正在尝试使用 R 在数据框中解决。以下是示例数据的列和几行:

我想编写一个函数来查找存在多个 FIPS 和多个 PROMO 的 ZIP。所以换句话说,ZIPS 与不同的 PROMO 交叉 FIPS。我不需要担心 COUNTY、FACTOR_X 和 FACTOR_Y,但我确实需要保留它们。

共有三种可能的促销级别(低、零、可变)。如果 ZIP 存在于多个 FIPS 中,并且 PROMO 在子集中不是不同的,则 STATUS 为 FAIL。但是,如果 ZIP 存在于多个 FIPS 中并且 PROMO 在子集中不同(相同),则 STATUS 为 PASS。

这里是一些示例输出

ZIP,ST_COUNTY,FIPS,FACTOR_X,FACTOR_Y,PROMO,STATUS

8520,NJ MERCER,34021,XXX,YYY,变量,失败

8520,NJ MIDDLESEX,34023,XXX,YYY,零,失败

8525,NJ XUNTERDON,34019,XXX,YYY,LOW,FAIL

8525,NJ MERCER,34021,XXX,YYY,变量,失败

8540,NJ MERCER,34021,XXX,YYY,变量,失败

8540,NJ MIDDLESEX,34023,XXX,YYY,零,失败

8540,NJ SOMERSET,34035,XXX,YYY,零,失败

8558,NJ XUNTERDON,34019,XXX,YYY,LOW,FAIL

8558,NJ MERCER,34021,XXX,YYY,变量,失败

8558,NJ SOMERSET,34035,XXX,YYY,零,失败

23117,VA GOOCXLAND,51075,XXX,YYY,零,失败

23117,VA LOUISA,51109,XXX,YYY,LOW,FAIL

23117,VA SPOTSYLVANIA,51177,XXX,YYY,LOW,FAIL

23117,VA SPOTSYLVANIA,51177,XXX,YYY,零,失败

78015,TX BEXAR,48029,XXX,YYY,零,失败

78015,TX BEXAR,48029,XXX,YYY,零,失败

78015,TX COMAL,48091,XXX,YYY,LOW,FAIL

78015,TX COMAL,48091,XXX,YYY,零,失败

78015,TX KENDALL,48259,XXX,YYY,LOW,FAIL

78015,TX KENDALL,48259,XXX,YYY,零,失败

1906,MA ESSEX,25009,XXX,YYY,LOW,PASS

1906,MA MIDDLESEX,25017,XXX,YYY,LOW,PASS

1906,马萨福克,25025,XXX,YYY,低,通过

16127,PA BUTLER,42019,XXX,YYY,零,通过

16127,PA 劳伦斯,42073,XXX,YYY,零,通过

16127,PA MERCER,42085,XXX,YYY,零,通过

16127,PA VENANGO,42121,XXX,YYY,零,通过

对于输出,我想将原始列和新的 STATUS 列拆分为两个文件。第一个文件是 ZIP_PASS,所有 STATUS == PASS,第二个文件是 ZIP_FAIL,所有 STATUS == FAIL

=======

【问题讨论】:

您应该明确提供与您的示例相对应的预期输出。详情:***.com/questions/5963269/… 感谢弗兰克的建议,按要求进行了编辑。 如果您将期望的 STATUS 列添加到示例数据中,将会有所帮助。前四行是否为 FAIL(因为它们都是 PROMO=LOW),而后四行是否为 PASS? 【参考方案1】:

这行得通吗?

library(dplyr)
df2 <- df1 %>% group_by(ZIP) %>%
  mutate(STATUS=c("PASS","FAIL")[(n_distinct(PROMO)==n())+1]) %>%
  ungroup

df_pass <- filter(df2,STATUS=="PASS")
df_fail <- filter(df2,STATUS=="FAIL")

# # A tibble: 8 x 7
# # Groups:   ZIP [4]
# ZIP     ST_COUNTY  FIPS FACTOR_X FACTOR_Y PROMO STATUS
# <int>         <chr> <int>    <chr>    <chr> <chr>  <chr>
# 1  1431  MA MIDDLESEX 25017      XXX      YYY   LOW   PASS
# 2  1431  MA WORCESTER 25027      XXX      YYY   LOW   PASS
# 3  1434  MA MIDDLESEX 25017      XXX      YYY   LOW   PASS
# 4  1434  MA WORCESTER 25027      XXX      YYY   LOW   PASS
# 5  4009 ME CUMBERLAND 23005      XXX      YYY  ZERO   FAIL
# 6  4009     ME OXFORD 23017      XXX      YYY   LOW   FAIL
# 7  4029 ME CUMBERLAND 23005      XXX      YYY  ZERO   FAIL
# 8  4029     ME OXFORD 23017      XXX      YYY   LOW   FAIL

数据

df1 <- read.table(text="ZIP,ST_COUNTY,FIPS,FACTOR_X,FACTOR_Y,PROMO
01431,MA MIDDLESEX,25017,XXX,YYY,LOW
01431,MA WORCESTER,25027,XXX,YYY,LOW
01434,MA MIDDLESEX,25017,XXX,YYY,LOW
01434,MA WORCESTER,25027,XXX,YYY,LOW
04009,ME CUMBERLAND,23005,XXX,YYY,ZERO
04009,ME OXFORD,23017,XXX,YYY,LOW
04029,ME CUMBERLAND,23005,XXX,YYY,ZERO
04029,ME OXFORD,23017,XXX,YYY,LOW",sep=",",header=T,stringsAsFactors=F)

【讨论】:

这太棒了!创建两个表并将其拆分可能只是 STATUS 上的过滤器,对吗? 是的,这些是表df_passdf_fail :) 为了安全起见,我在第一个查询末尾添加了 ungroup 语句 嘿弹涂鱼,我更新了这个问题来寻找三个级别的 PROMO。您提供的示例适用于两个级别,但不适用于三个级别。有什么建议吗? 也许是(n_distinct(PROMO) &gt;1) 而不是(n_distinct(PROMO)==n())

以上是关于如何编写 R 函数来查找数据框中的特定条件的主要内容,如果未能解决你的问题,请参考以下文章

使用“或”在熊猫数据框中选择值时如何编写条件[重复]

函数怎么写 函数如何写

编写一个 R 脚本来计算数据框中的平均值

如何分析特定函数在 R 中运行的时间长度

r中的选择性缩放函数使用不同的数据框进行缩放

如何编写测试用例以使用r中的testthat检查函数是否正常工作?