【问题标题】:How to get the unique values across selected row-column combination based on another column in R如何根据 R 中的另一列在选定的行列组合中获取唯一值
【发布时间】:2018-08-17 21:24:13
【问题描述】:

我有一个包含很多 NA 的 29 行和 26 列的数据框。数据看起来有点像下图(在 R 工作室工作)

V1 V2 V3 V4 V5 V6 V7 V8 V9 V10
a1 b1 d1 d2 d3 d4 d5 na na e2
a1 b2 d2 d4 d1 e2 na e1 na na
a1 b3 d5 d3 d1 d4 na na e1 e2
a2 c1 e1 e2 na e3 na d2 d1 d4
a2 c2 d2 d4 d1 e2 na e1 na na
a2 c3 d5 d3 d1 d4 na na e1 e2

这里我们有 V1-V10 列 a1 和 a2 是第 1 列中的 2 个不同值 V2 列中的 b1-b3 是与 V1 中的 a1 相关的不同值 V3-V10 列的每一行都有不同的值

我想要的结果如下-

NewV1 Newv2  NewV3
a1     3      7
a2     3      8

总结一下,我想根据 V1 获得(V2 值的总计数和 V3-V10 的不同值的计数)

【问题讨论】:

  • 不清楚 V3 的 7 和 8 是如何得到的
  • 这是我想要得到的结果..我还没有得到这个结果。

标签: r


【解决方案1】:

看起来,没有人可以重现您的结果。你的工作区分大小写吗? 如果是这样,对于dplyr 方法,您可以尝试:

# import libraries and data
library(tidyverse)

df <- read.table(text = "V1 V2 V3 V4 V5 V6 V7 V8 V9 V10
a1 b1 d1 d2 d3 d4 d5 NA NA E2
a1 b2 d2 d4 d1 E2 NA E1 NA NA
a1 b3 d5 d3 d1 d4 NA NA E1 E2
a2 c1 E1 E2 NA E3 NA D2 D1 D4
a2 c2 d2 d4 d1 E2 NA E1 NA NA
a2 c3 d5 d3 d1 d4 NA NA E1 E2", sep=" ", header = T, stringsAsFactors = F)

因为您的工作区分大小写,我们添加:

df <- data.frame(lapply(df, function(x) {
  if (is.character(x)) return(toupper(x))
  else return(x)
}))

现在运行:

 n_V2 <- df %>%
   gather(key, value, - V1, -V2) %>%
   group_by(V1) %>%
   distinct(V2) %>%
   summarise(Newv2=n())

 n_Vx <- df %>%
   gather(key, value, - V1, -V2) %>%
   filter(!is.na(value)) %>%
   group_by(V1) %>%
   distinct(value) %>%
   summarise(Newv3=n())  

 n_V2 %>% left_join(n_Vx)

输出完全是你的:

 Joining, by = "V1"
 # A tibble: 2 x 3
   V1    Newv2 Newv3
   <fct> <int> <int>
 1 a1        3     7
 2 a2        3     8

【讨论】:

  • 感谢您的帮助,但是基于 a1 和 a2 的 V3-V10 中的不同值总共是 7(对于 a1)和 8(对于 a2).. E1,E2,E3,d1, d2,d3,d4,d5...
  • 好的,从here添加了一行现在应该可以了,试试吧
  • 这可以在数据框上完成吗,导入一个 .csv 文件,因为我必须使用相同类型的数据,但稍后会有超过 10k 行。如何导入完整的数据,因为这里您已将其作为书面文本导入。
  • 当然,df &lt;- read_delim(file)read_delimreadr 中的一个函数,tidyverse 包。这取决于您的 csv 文件,但使用该功能应该不会出现问题。欲了解更多信息,请使用readr-documentation
【解决方案2】:

按照您的算法描述,您可以使用data.table

library("data.table")

dt <- fread(
"V1 V2 V3 V4 V5 V6 V7 V8 V9 V10
a1 b1 d1 d2 d3 d4 d5 NA NA E2
a1 b2 d2 d4 d1 E2 NA E1 NA NA
a1 b3 d5 d3 d1 d4 NA NA E1 E2
a2 c1 E1 E2 NA E3 NA D2 D1 D4
a2 c2 d2 d4 d1 E2 NA E1 NA NA
a2 c3 d5 d3 d1 d4 NA NA E1 E2")
dt[, .(nV2=length(V2), u3.10=uniqueN(na.omit(tolower(unlist(.SD))))), by=V1, .SDcols=3:10]
#    V1 nV2 u3.10
# 1: a1   3     7
# 2: a2   3     8

如果您有一个数据框 df,您可以通过以下方式将其强制转换为 data.table-object:

setDT(df)

【讨论】:

  • 感谢您的帮助,但是基于 a1 和 a2 的 V3-V10 中的不同值总共是 7(对于 a1)和 8(对于 a2).. E1,E2,E3,d1, d2,d3,d4,d5...
  • 请在您的问题中描述逻辑,即编辑您的问题:stackoverflow.com/posts/49191499/edit Do you want to count NA as a distinct value.对于 a2,我计算这些:E1、E2、E3、NA、D2、D1、D4、d2、d4、d1、d5、d3 - 是 12 或(没有 NA)11。D2 和 d2 是不同的值吗?我编辑了我的答案。
  • 现在我可以产生想要的结果了。
  • 这可以在数据框上完成吗,导入一个 .csv 文件,因为我必须使用相同类型的数据,但稍后会有超过 10k 行。如何导入完整数据,因为此处已将其作为书面文本导入。
  • fread() 可以读取 CSV 文件:阅读fread() 的帮助页面。如果您有一个数据框df,您可以使用setDT(df) 将其强制转换为data.table-object。
【解决方案3】:

您可以使用 data.table 来做到这一点:

library(data.table)
L3 <- LETTERS[1:3]
fac2 <- sample(L3, 10, replace = TRUE)
fac <- sample(L3, 10, replace = TRUE)
d <- data.frame(fac2 = fac2, fac = fac)
dd <- as.data.table(d)
dd[, num := length(unique(fac)), fac2]
dd[, mean(num), fac2]

最好的问候

【讨论】:

  • 谢谢你,但你能根据我的数据详细说明吗……有点困惑理解它。当我有相同类型的数据但有 10k 多行时,该方法也可以工作
猜你喜欢
  • 2020-02-08
  • 1970-01-01
  • 2021-07-22
  • 2020-10-09
  • 1970-01-01
  • 1970-01-01
  • 2019-11-10
  • 2011-10-02
  • 2015-08-03
相关资源
最近更新 更多