r-基于限制的数据帧中多列的频率列表



我有一个包含单词(第w1列、第w2列等(及其持续时间的df,其中一些是NA(第d1列、第d2列等(,比如这个:

set.seed(47)
df <- data.frame(
w1 = c(sample(LETTERS[1:4], 10, replace = T)),
w2 = c(sample(LETTERS[1:4], 10, replace = T)),
w3 = c(sample(LETTERS[1:4], 10, replace = T)),
w4 = c(sample(LETTERS[1:4], 10, replace = T)),
d1 = c(rep(NA, 3), round(rnorm(7),3)),
d2 = c(round(rnorm(6),3), NA, round(rnorm(3),3)),
d3 = c(round(rnorm(2),3), rep(NA,2), round(rnorm(6),3)),
d4 = c(round(rnorm(1),3), NA, round(rnorm(8),3))
)
w1 w2 w3 w4     d1     d2     d3     d4
1   D  A  A  C     NA -2.322 -0.693 -0.488
2   B  C  C  B     NA -1.967  0.261     NA
3   D  A  C  B     NA  0.028     NA  -0.92
4   D  C  A  A -1.566  0.484     NA  0.898
5   C  C  C  D  0.249  0.144  0.507 -0.356
6   C  D  B  B  -0.34   -1.2  0.564  1.032
7   B  B  A  A  0.417     NA  0.061  0.664
8   B  A  A  D -0.326  0.885 -0.109   0.97
9   C  A  C  B  -0.89  0.887 -0.155  1.676
10  D  B  D  C -1.608  0.001   0.95  1.988

我想得到的是在相应的持续时间列中所有而不是NA的单词标记的单一频率列表。因此,例如,列w1中的"D"在d1中为NA,因此该令牌不应包含在频率计数中。这是如何在R基中编程的,最好是在一行代码中?

忽略相应列中的NA值:

table(unlist(replace(df[paste0("w", 1:4)], is.na(df[paste0("d", 1:4)]), NA)))
#  B  C  D  A 
#  7 11  6  9 
# Alternate approach
table(unlist(df[1:4])[!is.na(unlist(df[5:8]))])
#  B  C  D  A 
#  7 11  6  9 

完全省略任何位置都有NA的值:

这是3行,但我会这样做:

all_words = unlist(df[1:4])
na_words = all_words[is.na(unlist(df[5:8]))]
table(droplevels(all_words[! all_words %in% na_words]))
# < table of extent 0 >

你可以在一行中完成,但它要丑陋得多,很难判断发生了什么。

table(droplevels(unlist(df[1:4])[! unlist(df[1:4]) %in% unlist(df[1:4])[is.na(unlist(df[5:8]))]]))

对于给定的样本数据,它给出了一个长度为0的表,因为所有唯一的单词在某个地方都有一个NA。如果您更改输入数据以使用更多字母,我们将得到非空结果:

set.seed(47)
df2 <- data.frame(
w1 = c(sample(LETTERS[1:8], 10, replace = T)),
w2 = c(sample(LETTERS[1:8], 10, replace = T)),
w3 = c(sample(LETTERS[1:8], 10, replace = T)),
w4 = c(sample(LETTERS[1:8], 10, replace = T)),
d1 = c(rep(NA, 3), round(rnorm(7),3)),
d2 = c(round(rnorm(6),3), NA, round(rnorm(3),3)),
d3 = c(round(rnorm(2),3), rep(NA,2), round(rnorm(6),3)),
d4 = c(round(rnorm(1),3), NA, round(rnorm(8),3))
)
table(droplevels(unlist(df2[1:4])[! unlist(df2[1:4]) %in% unlist(df2[1:4])[is.na(unlist(df2[5:8]))]]))
# F A 
# 5 4 

最新更新