Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/r/75.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
R 交叉列表多回答问题_R_Dplyr - Fatal编程技术网

R 交叉列表多回答问题

R 交叉列表多回答问题,r,dplyr,R,Dplyr,我需要通过一个分组变量交叉列出多个响应(存储为一组变量)。我的调查问题是:“你吃过以下哪种水果?”然后,来自地理区域1或区域2的受访者会得到一份标有“1.橙色,2.芒果,…”的列表,并且从是(1)或否(0)问题得出的结果数据是: set.seed(1) df <- data.frame(area=rep(c('Area 1','Area 2'), each=6), var_orange=sample(0:1, 12, T),

我需要通过一个分组变量交叉列出多个响应(存储为一组变量)。我的调查问题是:“你吃过以下哪种水果?”然后,来自地理区域1或区域2的受访者会得到一份标有“1.橙色,2.芒果,…”的列表,并且从是(1)或否(0)问题得出的结果数据是:

set.seed(1)
df <- data.frame(area=rep(c('Area 1','Area 2'), each=6),
                 var_orange=sample(0:1, 12, T),
                 var_banana=sample(0:1, 12, T),
                 var_melon=sample(0:1, 12, T),
                 var_mango=sample(0:1, 12, T))

     area var_orange var_banana var_melon var_mango
1  Area 1          0          1         0         1
2  Area 1          0          0         0         0
3  Area 1          1          1         0         1
4  Area 1          1          0         0         0
5  Area 1          0          1         1         1
6  Area 1          1          1         0         1
7  Area 2          1          0         0         1
8  Area 2          1          1         1         1
9  Area 2          1          1         0         1
10 Area 2          0          0         0         1
11 Area 2          0          1         1         0
12 Area 2          0          0         1         0
我发现了一个与multfreqtable函数相关的函数,该函数为我的数据提供单向摘要:

multfreqtable = function(data, question.prefix) {
  z = length(question.prefix)
  temp = vector("list", z)

  for (i in 1:z) {
    a = grep(question.prefix[i], names(data))
    b = sum(data[, a] != 0)
    d = colSums(data[, a] )
    e = sum(rowSums(data[,a]) !=0)
    f = as.numeric(c(d, b))
    temp[[i]] = data.frame(question = c(sub(question.prefix[i], 
                                            "", names(d)), "Total"),
                           freq = f,
                           percent_response = (f/b)*100,
                           percent_cases = round((f/e)*100, 2))
    names(temp)[i] = question.prefix[i]
  }
  temp
}

multfreqtable(df, "var_")

$var_
  question freq percent_response percent_cases
1   orange    6               24         54.55
2   banana    7               28         63.64
3    melon    4               16         36.36
4    mango    8               32         72.73
5    Total   25              100        227.27
但我对双向总结感兴趣

我可以使用a中建议的
dplyr
,并获得:


但我需要一个更整洁的表格输出,带有边缘列频率

使用
aggregate
的不同解决方案是

T1 = aggregate(df[,2:5], list(df$area), sum)
rownames(T1) = T1[,1]
T1 = t(T1[,-1])
T1 = addmargins(T1, 1:2, FUN = c(Total = sum), quiet=TRUE) 
T1
           Area 1 Area 2 Total
var_orange      3      3     6
var_banana      4      3     7
var_melon       1      3     4
var_mango       4      4     8
Total          12     13    25
感谢@rawr建议简化使用
addmargins

如果希望表格以百分比而不是计数表示,只需除以总计数即可得到分数,然后更改为百分比

T1 = aggregate(df[,2:5], list(df$area), sum)
rownames(T1) = T1[,1]
T1 = t(T1[,-1])
T1 = T1 * 100 / sum(T1)

T1 = addmargins(T1, FUN = c(Total = sum), quiet=TRUE) 
T1
           Area 1 Area 2 Total
var_orange     12     12    24
var_banana     16     12    28
var_melon       4     12    16
var_mango      16     16    32
Total          48     52   100

使用
aggregate
的另一种解决方案是

T1 = aggregate(df[,2:5], list(df$area), sum)
rownames(T1) = T1[,1]
T1 = t(T1[,-1])
T1 = addmargins(T1, 1:2, FUN = c(Total = sum), quiet=TRUE) 
T1
           Area 1 Area 2 Total
var_orange      3      3     6
var_banana      4      3     7
var_melon       1      3     4
var_mango       4      4     8
Total          12     13    25
感谢@rawr建议简化使用
addmargins

如果希望表格以百分比而不是计数表示,只需除以总计数即可得到分数,然后更改为百分比

T1 = aggregate(df[,2:5], list(df$area), sum)
rownames(T1) = T1[,1]
T1 = t(T1[,-1])
T1 = T1 * 100 / sum(T1)

T1 = addmargins(T1, FUN = c(Total = sum), quiet=TRUE) 
T1
           Area 1 Area 2 Total
var_orange     12     12    24
var_banana     16     12    28
var_melon       4     12    16
var_mango      16     16    32
Total          48     52   100

您可以首先使用
dplyr
计算值,然后使用
knitr::kable
等工具将其放入表格中

library(dplyr)
library(knitr)

set.seed(1)
df <- data.frame(area = rep(c('Area 1','Area 2'), each = 6),
                 var_orange = sample(0:1, 12, T),
                 var_banana = sample(0:1, 12, T),
                 var_melon = sample(0:1, 12, T),
                 var_mango = sample(0:1, 12, T))

t1 <- df %>% group_by(area) %>% summarise_each(funs(mean))
t2 <- df %>% summarise_each(funs(mean))
kable(rbind(t1, t2))
要进一步优化输出以模仿Stata的输出,请执行以下操作:

polished <- 100 * rbind(t1, t2) %>%  # Use percentages
  select(-area) %>%                  # Drop "area"
  mutate(Total = rowSums(.[])) %>%   # Add Total
  as.matrix %>% t

kable(polished, digits = 2, col.names = c("Area 1", "Area 2", "Total"))

您可以首先使用
dplyr
计算值,然后使用
knitr::kable
等工具将其放入表格中

library(dplyr)
library(knitr)

set.seed(1)
df <- data.frame(area = rep(c('Area 1','Area 2'), each = 6),
                 var_orange = sample(0:1, 12, T),
                 var_banana = sample(0:1, 12, T),
                 var_melon = sample(0:1, 12, T),
                 var_mango = sample(0:1, 12, T))

t1 <- df %>% group_by(area) %>% summarise_each(funs(mean))
t2 <- df %>% summarise_each(funs(mean))
kable(rbind(t1, t2))
要进一步优化输出以模仿Stata的输出,请执行以下操作:

polished <- 100 * rbind(t1, t2) %>%  # Use percentages
  select(-area) %>%                  # Drop "area"
  mutate(Total = rowSums(.[])) %>%   # Add Total
  as.matrix %>% t

kable(polished, digits = 2, col.names = c("Area 1", "Area 2", "Total"))

您可以从
?table
?prop.table
?addmargins
开始。示例输出中最下面的一行是sums,而最右边的一列是averages。这种不一致性使问题更加复杂。您可以从
?table
?prop.table
?addmargins
开始。示例输出中最下面的一行是sums,而最右边的一列是averages。这种不一致性使问题更加复杂。
addmargins
可用于
T1
addmargins(T1,1:2,FUN=c(Total=sum))
@rawr这是一个真正的改进。您介意我将其添加到我的解决方案中吗?@rawr看起来不错,但将表格值作为单元格百分比会更好。@amo将矩阵除以总数
T1/25*100
@G5W听起来不错,试试看
addmargins
可以在
T1
上使用,
addmargins(T1,1:2,FUN=c(total=sum))
@rawr这是一个真正的进步。您介意我将其添加到我的解决方案中吗?@rawr看起来不错,但将表格值作为单元格百分比会更好。@amo将矩阵除以总数
T1/25*100
@G5W听起来不错,可以这样做,但
summary_each()
会因应用
mean()而引发警告
在非数字区域列上。要解决此问题,可以通过
t2%summary_each(funs(mean))
限制函数仅作用于数字列。另一个问题是结果第三行的“NA”。我用
t2$area@amo替换了“Total”,当然,我已经修改了我的答案来模仿Stata输出。我宁愿忽略警告并保留NA,这样就可以简单地rbind t1和t2。我注意到
kable(抛光,align='c',digits=2,format=“pandoc”,caption=“表格标题”)
使输出更漂亮。可能值得添加?它可以工作,但在非数字区域列上应用
mean()
会引发警告。要解决此问题,可以通过
t2%summary_each(funs(mean))
限制函数仅作用于数字列。另一个问题是结果第三行的“NA”。我用
t2$area@amo替换了“Total”,当然,我已经修改了我的答案来模仿Stata输出。我宁愿忽略警告并保留NA,这样就可以简单地rbind t1和t2。我注意到
kable(抛光,align='c',digits=2,format=“pandoc”,caption=“表格标题”)
使输出更漂亮。也许值得补充一下?