用R语言做数据清理之一:数据的清理
数据的清理
一份好的,干净而整洁的数据至少包括以下几个要素:
1、每一个观测变量构成一列
2、每一个观测对象构成一行
3、每一个类型的观测单元构成一个表
就像我们最常接触的鸢尾花数据:
## Sepal.Length Sepal.Width Petal.Length Petal.Width Species
## 1 5.1 3.5 1.4 0.2 setosa
## 2 4.9 3.0 1.4 0.2 setosa
## 3 4.7 3.2 1.3 0.2 setosa
## 4 4.6 3.1 1.5 0.2 setosa
## 5 5.0 3.6 1.4 0.2 setosa
每一列就是观测的指标:花瓣长度,花瓣宽度,萼片长度,萼片宽度,种类;每一行就是一株鸢尾花的观测值,构成整张表的元素就是四个数值变量,一个分类分类变量。
然而出于排版的考虑我们抓下来的数据往往不是那么的友好,比如说我们可以看到的数据通常是这样的:
## religion <10k 10k-50k 50k-100k
## 1 Agnostic 12 31 23
## 2 Buddhist 58 43 43
## 3 Catholic 79 56 23
而不是:
## religion income freq
## 1 Agnostic <10k 12
## 2 Agnostic 10k-50k 58
## 3 Agnostic 50k-100k 79
## 4 Buddhist <10k 31
当然,除了这种把列表每一列代表一些数值这种情况外,还有多个变量储存为一列(比如列表不仅以"<10k","10k-50k","50k-100k"做表头,甚至还加上性别信息"m<10k","m10k-50k","m50k-100k","f<10k","f10k-50k","f50k-100k",其中m代表男性,f代表女性),还有更过分的将列表的变量不仅储存在列中,行中也有统计变量。
面对这些不好的table,我们首先要做的就是数据管理,将数据整理为一个干净的数据集。
数据管理
按照en:DAMA的定义:“数据资源管理,致力于发展处理企业数据生命周期的适当的建构、策略、实践和程序”。这是一个高层而包含广泛的定义,而并不一定直接涉及数据管理的具体操作(如关系数据库的技术层次上的管理)。我们这里主要讲述对于数据的变量命名与数据的合并,旨在方便数据共享。
数据管理首先要做的就是大致上了解你的数据,比如有什么样的变量,每一行大致长成什么样,最常用的就是head(),tail().
我们要做的基本上就是这么几项工作:
给每一个变量命名,而不是V1,V2,如果有必要可以给出code book。
每个变量名最好具有可读性,除非过长,否则不要用缩写,例如AgeAtDiagnosis这个命名远好于AgeDx。
通常来说,最好将数据放在一张表里面,如果因为数据过多,项目过杂,分成了几张表。那么一定需要有一列使得这些表之间能够连接起来,但尽量避免这样做。
我们以UCI的Human Activity Recognition Using Smartphones Data Set 为例来看看数据是如何变成一个基本符合要求的数据。这个数据我们已经下载下来了,其中关于数据的详细信息可以参阅read me文档,由于UCI的数据通常都是一个基本合乎规范的数据集(主要是指它的数据集的变量名都是以V1,V2来命名的)加上一个code book。那么我们看看各个数据的名称(在feature文件里)
setwd("F:/coursera/Data Science/peer assignment/get clean and tidy data/UCI HAR Dataset")name <- read.table("./features.txt", stringsAsFactors = F)
head(name)
## V1 V2
## 1 1 tBodyAcc-mean()-X
## 2 2 tBodyAcc-mean()-Y
## 3 3 tBodyAcc-mean()-Z
## 4 4 tBodyAcc-std()-X
## 5 5 tBodyAcc-std()-Y
## 6 6 tBodyAcc-std()-Z
我们可以看到各个特征的名称直接标在数据上是非常不友善的,我们为了让他具有可读性,我们以展示在我们眼前的6个数据为例:
variablename <- head(name)# 将标签中的大写字母转为小写,我们这里没有所以不再赋值,如果需要全变为大写,可以使用touppertolower(variablename$V2)
## [1] "tbodyacc-mean()-x" "tbodyacc-mean()-y" "tbodyacc-mean()-z"
## [4] "tbodyacc-std()-x" "tbodyacc-std()-y" "tbodyacc-std()-z"
# 将变量名分离成3部分splitNames <- strsplit(variablename$V2, "-")splitNames[[1]]
## [1] "tBodyAcc" "mean()" "X"
# 将变量名合成有意的名称named <- function(x) { rr <- paste(x[2], x[1], "-", x[3],sep = "")
chartr("()", "of", rr)
}
sapply(splitNames, named)
## [1] "meanoftBodyAcc-X" "meanoftBodyAcc-Y" "meanoftBodyAcc-Z"
## [4] "stdoftBodyAcc-X" "stdoftBodyAcc-Y" "stdoftBodyAcc-Z"
用这样的名字给数据集命名就感觉舒服多了,我们将一些R中对字符串常用的操作函数总结如下,方便我们对数据名称的修改:
sub:替换字符串中的第一个模式为设定模式(pattern).
gsub:全局替换字符串中的相应模式
grep,grepl:这两个函数返回向量水平的匹配结果,grep仅返回匹配项的下标,而grepl返回所有的查询结果,并用逻辑向量表示有没有找到匹配。
nchar:统计字符串单字数目
substr:取子串
paste:将字符串链接起来,sep参数可以设置连接符
str_trim:去掉字符串空格
变量的名称建议满足如下要求:
英文变量名尽可能用小写
尽可能的描述清楚变量特征 (Diagnosis versus Dx)
不要太复杂
不要有下划线、点、空格
字符型变量应该满足:
是因子类型的应该转化为factor
因子尽可能具有一定的描述性 (例如:如果0/1表示真假,那么用TRUE/FALSE代替0/1;在表示性别时用Male/Female代替M/F)
接下来我们讨论数据集的合并,主要使用函数merge。
我们以下面两个数据集的合并为例:
df1 <- data.frame(id = sample(1:10), reviewer_id = sample(5:14),time_left = sample(1321:1330),
x = rnorm(10))df2 <- data.frame(id = sample(1:10), answer = rep("B", 10),time_left = sample(321:330),
y = rnorm(10))
head(df1, n = 3)
## id reviewer_id time_left x
## 1 3 9 1326 -0.9232
## 2 10 5 1322 2.5069
## 3 1 14 1330 2.2478
head(df2, n = 3)
## id answer time_left y
## 1 1 B 329 0.8180
## 2 10 B 327 1.4639
## 3 9 B 323 0.8141
merge函数调用格式为:
merge(x, y, by = intersect(names(x), names(y)),
by.x = by, by.y = by, all = FALSE, all.x = all, all.y = all,
sort = TRUE, suffixes = c(".x",".y"),
incomparables = NULL, ...)
参数说明:
x,y:两个数据框
by, by.x, by.y:指定用于合并的列的名称。
all,all.x,all.y:默认的all = FALSE相当于自然连接, 或者说是内部链接. all.x = TRUE是一个左连接, all.y = TRUE是一个又连接, all = TRUE 相当于一个外部链接.
仔细观察下面3个例子你就会发现其中的奥秘:
mergedData <- merge(df1,df2,by.x="reviewer_id",by.y="id",all=TRUE)
head(mergedData)
## reviewer_id id time_left.x x answer time_left.y y
## 1 1 NA NA NA B 329 0.8180
## 2 2 NA NA NA B 330 -0.7706
## 3 3 NA NA NA B 325 -0.4851
mergedData <- merge(df1,df2,by.x="id",by.y="id",all=TRUE)
head(mergedData)
## id reviewer_id time_left.x x answer time_left.y y
## 1 1 14 1330 2.24783 B 329 0.8180
## 2 2 12 1324 1.03181 B 330 -0.7706
## 3 3 9 1326 -0.92317 B 325 -0.4851
## 4 4 7 1321 -0.07841 B 322 0.1801
mergedData2 <- merge(df1,df2,all=TRUE)
head(mergedData2)
## id time_left reviewer_id x answer y
## 1 1 329 NA NA B 0.8180
## 2 1 1330 14 2.2478 <NA> NA
## 3 2 330 NA NA B -0.7706
在plyr包中还提供了join,join_all,arrange等函数来实现表的连接,但我想merge这个函数已经足够用了,所以我们不在多说。当然,在极少数特别好的情况下(比如列的变量是一致的,或者行的观测个体是一致的时候)rbind,cbind也是有用的。
有些时候我们会遇到一些特殊的字符串:日期。R中提供了各式各样的函数来处理时间:
Sys.setlocale("LC_TIME", "C")
## [1] "C"
x <- c("1jan1960", "2jan1960", "31mar1960", "30jul1960")z <- as.Date(x, "%d%b%Y")
format(z, "%a %b %d")
## [1] "Fri Jan 01" "Sat Jan 02" "Thu Mar 31" "Sat Jul 30"
weekdays(z)
## [1] "Friday" "Saturday" "Thursday" "Saturday"
julian(z)
## [1] -3653 -3652 -3563 -3442
## attr(,"origin")
## [1] "1970-01-01"
transform(z, weekend = as.POSIXlt(z, format = "%Y/%m/%d")$wday %in% c(0, 6))
## X_data weekend
## 1 1960-01-01 FALSE
## 2 1960-01-02 TRUE
## 3 1960-03-31 FALSE
## 4 1960-07-30 TRUE
数据分析咨询请扫描二维码
《Python数据分析极简入门》 第2节 7 Pandas分组聚合 分组聚合(group by)顾名思义就是分2步: 先分组:根据某列数据的值进行 ...
2024-11-25数据分析需要学习的内容非常广泛,涵盖了从理论知识到实际技能的多个方面。以下是数据分析所需学习的主要内容: 数学和统计学 ...
2024-11-24数据分析师需要具备一系列多方面的技能和能力,以应对复杂的数据分析任务和业务需求。以下是数据分析师所需的主要能力: 统计 ...
2024-11-24数据分析师需要学习的课程内容非常广泛,涵盖了从基础理论到实际应用的多个方面。以下是根据我搜索到的资料整理出的数据分析师需 ...
2024-11-24《Python数据分析极简入门》 第2节 6 Pandas合并连接 在pandas中,有多种方法可以合并和拼接数据。常见的方法包括append()、conc ...
2024-11-24《Python数据分析极简入门》 第2节 5 Pandas数学计算 importpandasaspdd=np.array([[81,&n ...
2024-11-23数据分析涉及多个方面的学习,包括理论知识和实践技能。以下是数据分析需要学习的主要方面: 基础知识: 数据分析的基本概念 ...
2024-11-22数据分析适合在多个单位工作,包括但不限于以下领域: 金融行业:金融行业对数据分析人才的需求非常大,数据分析师可以从事经 ...
2024-11-22数据分析是一种涉及从大量数据中提取有用信息和洞察力的过程。其工作内容主要包括以下几个方面: 数据收集与整理:数据分析师 ...
2024-11-22数据分析师需要掌握多种技能,以确保能够有效地处理和分析数据,并为业务决策提供支持。以下是数据分析师需要掌握的主要技能: ...
2024-11-22数据开发和数据分析是两个密切相关但又有所区别的领域。以下是它们的主要区别: 定义和目标: 数据开发:数据开发涉及数据的 ...
2024-11-22数据架构师是负责设计和管理企业数据架构的关键角色,其职责涵盖了多个方面,包括数据治理、数据模型设计、数据仓库构建、数据安 ...
2024-11-22数据分析师需要具备一系列技能,以确保能够有效地处理、分析和解释数据,从而支持决策制定。以下是数据分析师所需的关键技能: ...
2024-11-22数据分析师需要具备一系列技能,以确保能够有效地处理、分析和解释数据,从而支持决策制定。以下是数据分析师所需的关键技能: ...
2024-11-22数据分析师需要具备一系列的技能和能力,以确保能够有效地处理、分析和解释数据,从而支持业务决策。以下是数据分析师所需的主要 ...
2024-11-22需求持续增长 - 未来数据分析师需求将持续上升,企业对数据驱动决策的依赖加深。 - 预测到2025年,中国将需要高达220万的数据人 ...
2024-11-22《Python数据分析极简入门》 第2节 4 Pandas条件查询 在pandas中,可以使用条件筛选来选择满足特定条件的数据 importpanda ...
2024-11-22数据分析师的工作内容涉及多个方面,主要包括数据的收集、整理、分析和可视化,以支持商业决策和问题解决。以下是数据分析师的一 ...
2024-11-21数据分析师必须掌握的技能可以从多个方面进行归纳和总结。以下是数据分析师需要具备的主要技能: 统计学基础:数据分析师需要 ...
2024-11-21数据分析入门的难易程度因人而异,总体来看,入门并不算特别困难,但需要一定的学习和实践积累。 入门难度:数据分析入门相对 ...
2024-11-21