使用RMarkdown自動化調查摘要

本指南介紹瞭如何使用RStudio自動使用R和R Markdown進行調查摘要。這對於不改變的文檔部分是很好的(例如,“調查顯示了實質上的黨派偏振”)。動機實際上是雙重的:效率(最大化代碼的可重用性,最小化複製和粘貼錯誤)和可重複性(最大化可以重現發現的人和計算機的數量)。

基本設置是編寫一個Rmd用作模板的文件,然後編寫一個循環遍歷每個數據文件的簡短R腳本(使用library(knitr))。所述render然後功能會將Rmd到文檔或幻燈片(通常在PDF,HTML或docx通過取文件元數據作爲)參數

有無數的方法來概括調查R.本指南介紹了一些基礎知識,ggplot和questionr,但着眼於整個工作流(文件管理等)。按照這裏的說明,您應該能夠重現所有四個報告(原則上,更多),儘管只編寫代碼來清理一個調查。大多數代碼都顯示在本文檔中,但所有代碼都可以在pewpoliticaltemplate.Rmd或中找到pew_report_generator.R。所有代碼以及輸出的文檔都可以在這裏找到,有關獲取數據的詳細信息,請參見下文。

軟件

RStudio的界面library(rmarkdown)正在迅速發展。強烈建議安裝當前版本的RStudio,特別是對於R Markdown代碼的預覽(此文檔是使用RStudio 1.1.83創建的)。(這是我的安裝指南,其中包含教程和備忘單的鏈接。有關更高級的調查數據清理,請單擊此處。)

即使你以前編織過Rmd,你的庫也可能不夠新,無法創建參數化報告。我建議安裝pacman,它具有便利功能p_load,可以平滑包安裝,裝載和維護。p_load如果你在Dropbox上進行合作,我會特別推薦。

install.packages("pacman")

p_load(rmarkdown, knitr, foreign, scales, questionr, tidyverse, update = TRUE)

記住PDF要求LaTeX (安裝鏈接)。相比之下,針織docx或HTML不需要LaTeX。pptx可以在R中創建library(ReporteRs),但這裏不討論。

數據

下載來自皮尤研究四個“政治調查”可以在這裏(即一月,三月,八月和十月2016)。你可能還記得,有些政治事件發生在2016年。(這些數據是免費的,只要你花一點時間來開帳戶。)

  • 如果需要,解壓縮每個zip文件夾。

我的三個文件夾都有直觀的名字(Jan16,Mar16和Oct16),但我的一個文件夾裏有一個冗長的名字,http___www.people-press.org_files_datasets_Aug16。別擔心。

  • 創建一個新文件夾,調用它,比如說automating。

  • 將所有四個數據文件夾移動到automating。

請注意,我與Pew Research沒有任何關係(過去或現在)。我只是認爲他們做了很棒的工作,並且他們可以相對輕鬆地開始使用有意義的數據集。

Markdown 模版

在RStudio中,創建一個新的R筆記本並將其保存爲剛剛創建pewpoliticaltemplate.Rmd的automating文件夾。該文件可能HTML默認編織; 按住編織按鈕將其更改爲PDF。根據需要向標題添加字段。下面的示例標題通過解析Date:R代碼旁邊的表達式自動將今天的日期放在文檔上。classoption: landscape可能有助於廣泛的表格。您還可以使用多種格式指定包含參考書目的文件,例如BibTex和EndNote (引文詳細信息)

接下來添加一個R代碼塊來pewpoliticaltemplate.Rmd處理格式化等背景內容。雖然只需編織設置工作目錄Rmd,但必須設置目錄knitr::opts_knit$set(root.dir = '...')以自動執行文檔準備。(如果您仍在編輯,setwd則不需要Rmd,但Console建議單獨設置工作目錄。)

[圖片上傳失敗...(image-37c147-1547913882066)]

右上角的“播放”按鈕可以預覽代碼的輸出,非常方便。如果分析的某些部分非常冗長,則只需運行一次,即可讓您對圖形等進行修補。

  • 現在已經設置了默認設置,您無需擔心每個代碼塊都會抑制警告等。當然,您可以根據需要逐個更改它們。

  • 與R不同,在設置單個代碼塊的格式選項時(如上所示,在默認啓動之前禁止顯示警告),您需要輸入單詞TRUE並FALSE完整填寫。

  • 與模板不同,在本文檔中,我將默認值設置爲echo = TRUE並tidy = TRUE更好地顯示R代碼。

  • 該設置asis = TRUE對專業格式的表非常有用(如下所示),但不建議用於矩陣和表的原始R輸出。要kable默認顯示原始數據框,請參見此處

我發現最簡單的方法是編寫一個完整的工作示例,然後根據需要進行少量更改,以便knitr::render()循環遍歷數據集。首先要做的事情。

survey <- read.spss("Jan16/Jan16 public.sav", to.data.frame = TRUE)

可以輕鬆地將摘要統計信息插入到文本中,如下所示:

[圖片上傳中...(image-a6b159-1547913649827-0)]

該模板包含具有調查權重的其他示例(較長的計算應在代碼塊中完成,然後使用該內聯樣式引用其結果)。

這是我們可能想要的基本情節,它反映了調查權重。facet_grid()用於爲每個參與方識別創建類似的圖。該圖使用稍微不穩定的語法y = (..count..)/sum(..count..)將結果顯示爲百分比而不是計數。請注意,爲簡潔起見,省略了一些清理數據的代碼(主要是縮短標籤),但可以在此處找到。

我發現最簡單的方法是編寫一個完整的工作示例,然後根據需要進行少量更改,以便knitr::render()循環遍歷數據集。首先要做的事情。

survey <- read.spss("Jan16/Jan16 public.sav", to.data.frame = TRUE)

可以輕鬆地將摘要統計信息插入到文本中,如下所示:


該模板包含具有調查權重的其他示例(較長的計算應在代碼塊中完成,然後使用該內聯樣式引用其結果)。

這是我們可能想要的基本情節,它反映了調查權重。facet_grid()用於爲每個參與方識別創建類似的圖。該圖使用稍微不穩定的語法y = (..count..)/sum(..count..)將結果顯示爲百分比而不是計數。請注意,爲簡潔起見,省略了一些清理數據的代碼(主要是縮短標籤),但可以在此處找到。

PA <- ggplot(survey) + theme_minimal()
PA <- PA + geom_bar(aes(q1, y = (..count..)/sum(..count..), weight = weight, 
    fill = q1))
PA <- PA + facet_grid(party.clean ~ .) + theme(strip.text.y = element_text(angle = 45))
PA <- PA + xlab("") + ylab("Percent of Country")
PA <- PA + ggtitle("Presidential Approval: January 2016")
PA <- PA + scale_y_continuous(labels = scales::percent)
PA

以下是加權交叉表的示例。knitr::kable將創建一個專業的表格(當編織時PDF; kable採用學術期刊的風格)。
kable(wtd.table(surveyideo, surveysex, survey$weight)/nrow(survey), digits = 2)

假設我們要顯示總統批准,其中第一列提供整體批准,後續列是各種感興趣因素的交叉表(使用單元格權重)。我寫了一個名爲Xtabs的便利函數來創建這種格式,這在調查領域很常見。

source("[https](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[://](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[raw](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[.](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[githubusercontent](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[.](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[com](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[/](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[rdrr1990](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[/](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[datascience101](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[/](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[master](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[/](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[automating](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[/](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[Xtabs](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[.](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)[R](https://raw.githubusercontent.com/rdrr1990/datascience101/master/automating/Xtabs.R)")

kable(Xtabs(survey, "q1", c("sex", "race"), weight = "cellweight"))

假設我們想做很多交叉表。語法survey$ideo被廣泛用於方便,但survey[["ideo"]]它將更好地爲我們服務,因爲它允許我們使用變量名稱的向量(來自win-vector的細節)。下面,前兩個比較調用是相同的,但最後一個不是因爲數據框中沒有變量“x” survey。

identical(survey$ideo, survey[["ideo"]])
[1] TRUE
x <- "ideo"
identical(survey[[x]], survey[["ideo"]])
[1] TRUE
identical(survey[[x]], survey$x)
[1] FALSE

所以說我們希望所有問題20,21,22交叉的意識形態和黨ID的加權交叉表.29。這裏有一些代碼可以做到這一點。

x <- names(survey)[grep("q2[[:digit:]]", names(survey))]
x
 [1] "q20"  "q21"  "q22a" "q22b" "q22c" "q22d" "q22e" "q22f" "q22g" "q22h"
[11] "q22i" "q25"  "q26"  "q27"  "q28" 
y <- c("ideo", "party")
for (i in x) {
    for (j in y) {
        cat("\nWeighted proportions for", i, "broken down by", j, "\n")
        print(kable(wtd.table(survey[[i]], survey[[j]], survey$weight)/nrow(survey), 
            digits = 2))
        cat("\n")  # break out of table formatting
    }
    cat("\\newpage")
}

幾點說明:

  • 此代碼僅適用於asis設置(如上所示),該設置允許knitr將輸出解釋print(kable())爲要呈現的內容(而不僅僅是顯示用於其他地方的Markdown代碼)。

  • 理想情況下,人們會有一個csv或data.frame多個問題,並將其顯示爲循環切換問題。在這種情況下,調查問卷是在一個docx,所以library(docxtrackr)可能有所幫助。

  • 而不是嵌套循環,人們可能更願意選擇一個問題,循環交叉表的人口統計和意識形態類別,然後插入評論和概述。

  • 外部循環在每次運行時都會生成一個新頁面,內部循環使用cat("\newpage")),特定於渲染爲PDF。\n需要額外的換行符來打破錶格格式並保持代碼和文本分開。docx需要一種不同的分頁方法。

使用參數調整模版

下一步是添加一個包含所需變量的參數。參數將由下面討論的R腳本控制。當然,對於由哪個文件控制的內容有很多選擇,但通常只需要少量參數。將以下內容添加到標題的末尾pewpoliticaltemplate.Rmd:

這會創建變量paramsspssfile並且paramssurveywave可以從其他R會話外部控制,1並2016分別給出它們的默認值。設置默認值可以讓你繼續Rmd自己編織(而不是從我們稍後會創建的R腳本中設置默認值...您也可以單擊Knit並選擇Knit with Parameters指定特定值)。
現在對Rmd模板進行任何更改。例如,在ggplot代碼中......

PA <- PA + ggtitle(paste("Presidential Approval:", params$surveywave))

請注意,我們可以獲得所有spss文件的列表,如下所示:

dir(pattern = "sav", recursive = TRUE)

[1] "http___[www.people-press.org_files_datasets_Aug16/Aug16](http://www.people-press.org_files_datasets_aug16/Aug16)public.sav"

[2] "Jan16/Jan16 public.sav"                                           

[3] "March16/March16 public.sav"                                       

[4] "Oct16/Oct16 public.sav"

或者在這種情況下

dir(pattern = "16 public.sav", recursive = TRUE)

[1] "http___[www.people-press.org_files_datasets_Aug16/Aug16](http://www.people-press.org_files_datasets_aug16/Aug16)public.sav"

[2] "Jan16/Jan16 public.sav"                                           

[3] "March16/March16 public.sav"                                       

[4] "Oct16/Oct16 public.sav"

如果您或您的協作者添加spss具有相似名稱的其他文件,我建議儘可能使模式具體。要使用正則表達式指定更復雜的模式,請參見此處

現在回到編輯pewpoliticaltemplate.Rmd......


使用這些默認設置編織文件以查看其外觀; 就是這個部分。

knitr 自動化

現在創建一個新的R腳本; 我的叫pew_report_generator.R。它只是一個簡單的循環,它告訴要抓取哪個數據集,以及要傳遞給的標籤Rmd。請注意,標籤按字母順序而不是按時間順序顯示,作爲Rmd查找文件的方式的函數。

library(pacman)
p_load(knitr, rmarkdown, sessioninfo)

setwd("/users/mohanty/Desktop/pewpolitical/")

waves <- c("August 2016", "January 2016", "March 2016", "October 2016")

for (i in 1:length(waves)) {
    render("pewpoliticaltemplate.Rmd", params = list(spssfile = i, surveywave = waves[i]), 
        output_file = paste0("Survey Analysis ", waves[i], ".pdf"))
}

session <- session_info()
save(session, file = paste0("session", format(Sys.time(), "%m%d%Y"), ".Rdata"))

而已。當然,在實踐中,您可能會在第一次調查中編寫一些代碼,但這些代碼並不適用於所有這些代碼。例如,皮尤似乎在最近兩次調查中對調查日期的格式不同,這使我做了一些改變。但是,如果數據的格式相當一致,那麼一次性投資可以節省大量的時間,使其容易出錯,並且容易出錯。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章