有效地将标记变量转换为因子
Efficiently converting labelled variables to factors
我正在努力寻找有效地将标记变量转化为因子的方法。我正在使用的数据集可从此处获得:
[https://www.dropbox.com/s/jhp780hd0ii3dnj/out.sav?dl=0][1]。
是一个spss数据文件,因为同事用的东西,所以我喜欢用。
当我读入数据时,您可以看到文件中的每一个因素都变成了 "labelled" class。
#load libraries
library(haven)
library(tidy)
library(dplyr)
#Import
test<-read_sav(path='~/your/path/name/out.sav')
#Structure
str(test)
#Find Class
sapply(test, class)
我遇到的第一个问题是 ggplot2 不知道如何将比例应用于标记 class。
#
td<-ford %>%
select(income, stress) %>%
group_by(income, stress)%>%
filter(is.na(stress)==FALSE)%>%
filter(is.na(income)==FALSE)%>%
summarize(Freq=n())%>%
mutate(Percent=(Freq/sum(Freq))*100)
#Draw plot
ggplot(td, aes(x=income, y=Percent, group=stress))+
#barplot
geom_bar(aes(fill=stress), stat='identity')
通过将分类变量 'income' 包装在 as_factor()
中可以很好地解决这个问题
#Draw plot
ggplot(td, aes(x=as_ford(income), y=Percent, group=stress))+
#barplot
geom_bar(aes(fill=stress), stat='identity')
这对 rone 变量有效,但是,如果我正在进行探索性研究,我可能会做很多带有很多标记变量的图。这给我留下了相当多的额外输入。
当您收集大量变量来绘制多个交叉表时,这个问题会被放大,您会丢失值标签。
##Visualizations
test<-ford %>%
#The first two variables are the grouping, variables for a series of cross tabs
select(ford, stress,resp_gender, immigrant2, education, property, commute, cars, religion) %>%
#Some renamings
rename(gender=resp_gender, educ=education, immigrant=immigrant2, relig=religion)%>%
#Melt all variables other than ford and stress
gather(variable, category, -ford, -stress)%>%
#Group by all variables
group_by(variable, category, ford, stress) %>%
#filter out missings
filter(is.na(stress)==FALSE&is.na(ford)==FALSE)%>%
#filter out missings
filter(is.na(value)==FALSE)%>%
#summarize
summarize(freq=n())
#Show plots
ggplot(test, aes(x=as_factor(value), y=freq, group=as_factor(ford)))+geom_bar(stat='identity',position='dodge', aes(fill=as_factor(ford)))+facet_grid(~category, scales='free')
所以,现在所有被融化的变量的值标签都消失了。因此,我能看到的防止这种情况的唯一方法是单独使用 as_factor() 将每个标记变量转换为一个以值标签作为因子水平的因子。但是,同样,这是很多打字。
我想我的问题是如何最有效地处理标记的 class,将它们转化为因子,特别是关于 ggplot2。
已经有一段时间了,评论中已经有了答案,但我还是会 post 使用 dplyr
来回答。
library(haven)
# Load Stata file and look at it
nlsw88 <- read_dta('http://www.stata-press.com/data/r15/nlsw88.dta')
head(nlsw88)
我们看到有一些带标签的变量。如果我们只想转换特定的变量,我们可以使用mutate_at
from dplyr
。
# Convert specific variables to factor
nlsw88 %>%
mutate_at(
vars('race'),
funs(as_factor(.))
) %>%
head()
根据 Gregor 和 aosmith 的评论,我们还可以使用 mutate_if
函数转换所有标记变量,测试 labelled
class。这将为您节省大量额外的输入。
# Convert all labelled variables to factor
nlsw88 %>%
mutate_if(
is.labelled,
funs(as_factor(.))
) %>%
head()
这可用于创建类似于您所描述的条形图(尽管这个特定的图可能没有多大意义):
nlsw88 %>%
select(race, married, collgrad, union) %>%
mutate_if(
is.labelled,
funs(as_factor(.))
) %>%
gather(variable, category, -c(race, married)) %>%
group_by(race, married, variable, category) %>%
summarise(freq = n()) %>%
filter(!is.na(category)) %>%
ggplot(aes(x = category, y = freq)) +
geom_bar(stat = 'identity', aes(fill=race)) +
facet_grid(~married)
我正在努力寻找有效地将标记变量转化为因子的方法。我正在使用的数据集可从此处获得: [https://www.dropbox.com/s/jhp780hd0ii3dnj/out.sav?dl=0][1]。 是一个spss数据文件,因为同事用的东西,所以我喜欢用。
当我读入数据时,您可以看到文件中的每一个因素都变成了 "labelled" class。
#load libraries
library(haven)
library(tidy)
library(dplyr)
#Import
test<-read_sav(path='~/your/path/name/out.sav')
#Structure
str(test)
#Find Class
sapply(test, class)
我遇到的第一个问题是 ggplot2 不知道如何将比例应用于标记 class。
#
td<-ford %>%
select(income, stress) %>%
group_by(income, stress)%>%
filter(is.na(stress)==FALSE)%>%
filter(is.na(income)==FALSE)%>%
summarize(Freq=n())%>%
mutate(Percent=(Freq/sum(Freq))*100)
#Draw plot
ggplot(td, aes(x=income, y=Percent, group=stress))+
#barplot
geom_bar(aes(fill=stress), stat='identity')
通过将分类变量 'income' 包装在 as_factor()
中可以很好地解决这个问题#Draw plot
ggplot(td, aes(x=as_ford(income), y=Percent, group=stress))+
#barplot
geom_bar(aes(fill=stress), stat='identity')
这对 rone 变量有效,但是,如果我正在进行探索性研究,我可能会做很多带有很多标记变量的图。这给我留下了相当多的额外输入。
当您收集大量变量来绘制多个交叉表时,这个问题会被放大,您会丢失值标签。
##Visualizations
test<-ford %>%
#The first two variables are the grouping, variables for a series of cross tabs
select(ford, stress,resp_gender, immigrant2, education, property, commute, cars, religion) %>%
#Some renamings
rename(gender=resp_gender, educ=education, immigrant=immigrant2, relig=religion)%>%
#Melt all variables other than ford and stress
gather(variable, category, -ford, -stress)%>%
#Group by all variables
group_by(variable, category, ford, stress) %>%
#filter out missings
filter(is.na(stress)==FALSE&is.na(ford)==FALSE)%>%
#filter out missings
filter(is.na(value)==FALSE)%>%
#summarize
summarize(freq=n())
#Show plots
ggplot(test, aes(x=as_factor(value), y=freq, group=as_factor(ford)))+geom_bar(stat='identity',position='dodge', aes(fill=as_factor(ford)))+facet_grid(~category, scales='free')
所以,现在所有被融化的变量的值标签都消失了。因此,我能看到的防止这种情况的唯一方法是单独使用 as_factor() 将每个标记变量转换为一个以值标签作为因子水平的因子。但是,同样,这是很多打字。
我想我的问题是如何最有效地处理标记的 class,将它们转化为因子,特别是关于 ggplot2。
已经有一段时间了,评论中已经有了答案,但我还是会 post 使用 dplyr
来回答。
library(haven)
# Load Stata file and look at it
nlsw88 <- read_dta('http://www.stata-press.com/data/r15/nlsw88.dta')
head(nlsw88)
我们看到有一些带标签的变量。如果我们只想转换特定的变量,我们可以使用mutate_at
from dplyr
。
# Convert specific variables to factor
nlsw88 %>%
mutate_at(
vars('race'),
funs(as_factor(.))
) %>%
head()
根据 Gregor 和 aosmith 的评论,我们还可以使用 mutate_if
函数转换所有标记变量,测试 labelled
class。这将为您节省大量额外的输入。
# Convert all labelled variables to factor
nlsw88 %>%
mutate_if(
is.labelled,
funs(as_factor(.))
) %>%
head()
这可用于创建类似于您所描述的条形图(尽管这个特定的图可能没有多大意义):
nlsw88 %>%
select(race, married, collgrad, union) %>%
mutate_if(
is.labelled,
funs(as_factor(.))
) %>%
gather(variable, category, -c(race, married)) %>%
group_by(race, married, variable, category) %>%
summarise(freq = n()) %>%
filter(!is.na(category)) %>%
ggplot(aes(x = category, y = freq)) +
geom_bar(stat = 'identity', aes(fill=race)) +
facet_grid(~married)