【问题标题】:choosing data frames from within a list of data frames从数据框列表中选择数据框
【发布时间】:2017-11-29 20:13:26
【问题描述】:

我正在尝试根据某些列是否为空,从一长串数据框中选择数据框。

这是一个可重现的示例,以及我为尝试解决此问题而编写的代码。我正在使用一个随机变量作为另一个随机变量的可接受替代品(这里,b 代表 c),所以如果 df1 a 最终同时出现在第 1 组和第 2 组中,我不会感到困扰。

d1 <- data.frame(a=rnorm(5), b=1:5, c=rnorm(5))
d2 <- data.frame(a=1:5, b=rnorm(5), c = c(NA, NA, NA, NA, NA))
d3 <- data.frame(a=1:5, b=c(NA, NA, NA, NA, NA), c=c(1:5))

my_test_data <- list(d1, d2, d3)
group_1 <- list()
group_2 <- list()

for (i in 1:length(my_test_data)) {
if(!is.nan(my_test_data[[i]]$b)) {
group_1[i] <- my_test_data[i]
}
else if (!is.nan(my_test_data[[i]]$c)) {
group_2[i] <- my_test_data[i]
}
else NULL
}

我收到警告消息说:

警告信息: 1: 在 if (!is.nan(my_test_data[[i]]$b)) { : 条件的长度 > 1 并且只使用第一个元素

组 1 和组 2 与 my_test_data 相同

非常感谢所有帮助。

【问题讨论】:

  • is.nanis.na 测试整个向量并返回列长度相同的向量,例如检查 is.na(d2$c) 的输出
  • 谢谢你 - 所以这种方法行不通。您对我如何做到这一点有什么建议吗?

标签: r list for-loop if-statement


【解决方案1】:

您的示例代码中出现了几个问题。

您收到警告的原因是您的 if 条件正在返回一个向量。

is.nan(my_test_data[[3]]$b) 
[1] FALSE FALSE FALSE FALSE FALSE`

您遇到的第二个问题是您的示例数据没有任何NaN 值。你有 NA 值......所以 is.nan() 无论如何都找不到任何东西。

您遇到的第三个问题是您的 if / else if / else 格式不正确。 else if 与大括号 } else if () { 位于同一行

第四个问题是NULL 本身并没有做任何事情。您不妨忽略else NULL,因为它没有任何作用。或者你可以改变它来做一些事情。

我们可以检查TRUE %in% is.na()是否不是!is.na()

for (i in 1:length(my_test_data)) {
    if(TRUE %in% is.na(my_test_data[[i]]$b)) {
      group_1[i] <- my_test_data[i]
    } else if (TRUE %in% is.na(my_test_data[[i]]$c)) {
      group_2[i] <- my_test_data[i]
    } # else {
    #   NULL
    # }
}

现在,您的代码仍然会有一些奇怪的列表,因为您在列表中存储了 NULL 值,但我不确定这是否适合您正在做的事情。

str(group_1)

List of 3
$ : NULL
$ : NULL
$ :'data.frame':    5 obs. of  3 variables:
    ..$ a: int [1:5] 1 2 3 4 5
    ..$ b: logi [1:5] NA NA NA NA NA
    ..$ c: int [1:5] 1 2 3 4 5

【讨论】:

  • 使用 TRUE/FALSE 向量时的另一个技巧是 sum() 命令。例如,您可以使用if( sum(is.na(my_test_data[[i]]$b)) &gt; 0) { do something }。此命令检查任何值是否为真,因为 FALSE 始终为零并且所有零之和为零。
  • 非常感谢您抽出宝贵的时间阅读。通过阅读并与我之前的代码进行比较,我学到了很多东西。我正在学习 R 语言并进行雄心勃勃的分析来自学 - 非常感谢。
  • @AdamSampson +1,很好地解释了 OP 遇到问题的地方,尽管我认为使用 any(is.na(...)) 而不是 TRUE %in% is.na(...) 更习惯用法
  • 好点。 any() 更具可读性。有时我的大脑会卡住。大声笑。
猜你喜欢
  • 2019-03-04
  • 1970-01-01
  • 1970-01-01
  • 2015-12-25
  • 1970-01-01
  • 1970-01-01
  • 2021-10-26
  • 1970-01-01
  • 2011-08-17
相关资源
最近更新 更多