计数整个数据框的值

时间:2019-02-19 14:20:25

标签: r dataframe dplyr

我有这个数据框:

> df
   X1 X2 X3 X4 X5 X6 X7
1   2  7  2  3  5  6  7
2   4  2  3  6  1 NA  3
3   3  6  4  4  4  7  7
4   6  5  6 NA  3  1  7
5   1  1  2  3  3  3  7
6   4  7  2  4  5  4  2
7   5 NA  4  5  2  2  3
8   3  7  2  4  4  1  5
9   4  5  6  2  5  6  3
10  2  4  6  4  5  6  3

我想计算数字1,2,3,4并将其分配给x6,7并将其分配给y,并将所有数字(1,2,3,4,5,6,7)分配给z。之后,我将计算y/z - x/z

我已经用table(unlist(df))并单独分配了值之后完成了此操作。但是,我正在寻找一种没有循环或apply()的解决方案,因为我看不到升级它们的方法,因为我有近100列和10.000行(我知道它们都是从1开始的整数至7和NA values)。

我正在寻找这样的解决方案:

x <- count(df, c(1,2,3,4), na.rm = TRUE)
y <- count(df, c(6,7), na.rm = TRUE)
z <- count(df, c(1,2,3,4,5,6,7), na.rm = TRUE)

但是,似乎count()不能像那样工作,也不存在执行该操作的函数。

有什么建议吗?

3 个答案:

答案 0 :(得分:4)

基本的R解决方案。

vec <- unlist(df)

vec_c <- table(vec)

x <- sum(vec_c[names(vec_c) %in% as.character(1:4)])
y <- sum(vec_c[names(vec_c) %in% as.character(6:7)])
z <- sum(vec_c)

y/z - x/z
# [1] -0.358209

另一个想法。

vec <- unlist(df)

x <- sum(vec %in% 1:4)
y <- sum(vec %in% 6:7)
z <- length(vec[!is.na(vec)])

y/z - x/z
# [1] -0.358209

另一个想法。

m <- as.matrix(df)

x <- sum(m %in% 1:4)
y <- sum(m %in% 6:7)
z <- sum(!is.na(df))

y/z - x/z
# [1] -0.358209

数据

df <- read.table(text = "   X1 X2 X3 X4 X5 X6 X7
1   2  7  2  3  5  6  7
                 2   4  2  3  6  1 NA  3
                 3   3  6  4  4  4  7  7
                 4   6  5  6 NA  3  1  7
                 5   1  1  2  3  3  3  7
                 6   4  7  2  4  5  4  2
                 7   5 NA  4  5  2  2  3
                 8   3  7  2  4  4  1  5
                 9   4  5  6  2  5  6  3
                 10  2  4  6  4  5  6  3",
                 header = TRUE)

答案 1 :(得分:1)

这里是使用tidyverse

的选项
library(tidyverse)
gather(df, na.rm = TRUE) %>%
   count(value) %>% 
   mutate(n1 = sum(n)) %>%
   filter(value %in% c(1:4, 6:7)) %>% 
   group_by(grp = value %in% 1:4) %>% 
   summarise(perc = sum(n)/first(n1)) %>% 
   summarise(z = diff(perc))
# A tibble: 1 x 1
#      z
#   <dbl>
# 1 0.358

答案 2 :(得分:1)

另一种方法坚持使用table(),将计数结构放入列表中。

count <- setNames(lapply(list(1:4, 6:7, 1:7), function(x){
  tab <- table(unlist(d))
  return(sum(tab[x]))
 }), tail(letters, 3))

> with(count, y/z - x/z)
[1] -0.358209

数据

d <- structure(list(X1 = c(2L, 4L, 3L, 6L, 1L, 4L, 5L, 3L, 4L, 2L), 
    X2 = c(7L, 2L, 6L, 5L, 1L, 7L, NA, 7L, 5L, 4L), X3 = c(2L, 
    3L, 4L, 6L, 2L, 2L, 4L, 2L, 6L, 6L), X4 = c(3L, 6L, 4L, NA, 
    3L, 4L, 5L, 4L, 2L, 4L), X5 = c(5L, 1L, 4L, 3L, 3L, 5L, 2L, 
    4L, 5L, 5L), X6 = c(6L, NA, 7L, 1L, 3L, 4L, 2L, 1L, 6L, 6L
    ), X7 = c(7L, 3L, 7L, 7L, 7L, 2L, 3L, 5L, 3L, 3L)), class = "data.frame", row.names = c("1", 
"2", "3", "4", "5", "6", "7", "8", "9", "10"))