上一篇:《Using OpenRefine》翻译~9
第三章:高级数据操作
上一章中,我们介绍了OpenRefine的一些基本的操作。然而这些仅仅提供了你初级的数据分析处理技能。只有OpenRefine高级特性才能让你领略其真正的强大之处,本章就将介绍这些内容:
• 点1:对多值单元格的处理
• 点2:行模式和记录模式的转换
• 点3:相似单元格聚类
• 点4:单元格值转换
• 点5:增加源列
• 点6:拆分列
• 点7:行列转换
以上要点你可以自由选择学习。在本章学习前,你需要使用已经清理过的数据集,这可以在PACKT网站下载。学习这些要点中的任何部分都可以让你成为OpenRefine高级用户。但是请注意:有些数据操作特别重要。
点1:对多值单元格的处理
在很多表格数据中有一个普遍的问题:如果一个单元格中有多个值怎么办?举个例子,如果有一张包含名字、地址、电话号码的客户信息表格。录入人员正在对这张表格进行信息录入,当其发现有一个名字为Mr.Thompson的人有两个地址信息,并且每个地址信息对应一个电话号码,一般情况下录入人员会选择下面三种可能的操作:
• 只增加一个地址信息:这是最简单的做法,这减少了一般的录入工时。但是,这也意味着丢失了一般的信息,所以表格信息完整性被降低了。
• 增加两行:虽然现在表格信息是完整了,但是数据却出现了冗余。数据冗余也不好,因为这很容易导致错误:这两行可能会被认为是两个不同的都叫Mr.Thompson的人的信息,但如果这是Mr.Thompson不同时间所留下的信息,就容易导致错误。另外,因为这两行没有什么联系,如果其中一行信息被更新了,另一行并不能自动更新。
• 在一行中添加所有信息:这种情况下,两个地址信息和两个电话信息都被添加到对应字段中一个单元格内。但是对于原先字段的定义来说,我们这样操作可以说是信息超载了。当然这样操作对于信息来说是符合完整和非冗余,但是也会有个问题。对于我们人类来说我们可以毫不费力的识别出这些信息含义,但是计算机却做不到。想象下一个写信的人在信封上写了两个不同的地址;或者是一台自动拨号机,其是通过将一个单元格的所有内容作为一个电话号码来进行拨出。上面两种情况都会产生错误。所以字段确实丢失了语义上的精确性。
虽然我们知道我们有很多种技术方法可以解决多值单元格问题,比如表格关联。但是,如果数据模型你不能控制,那么你也就只能选择上面三种中的一种。
幸运的是,OpenRefine可以做到多值单元格的识别。当然因为OpenRefine是一种自动化软件,所以其需要在操作前指定某个字段为multi-valued多值字段。在Powerhouse Museum数据集中,Categories列就包含多值单元格,因为其单元格内容可以属于不同的分类。在我们进行操作前,我们必须告诉OpenRefine这个字段是有点不同的。
假如我们想了解Categories列中究竟有多少不同的分类,并且哪个分类数量最多。那么首先让我们看看,如果我们对Categories进行文本透视会发生什么(Facet| Text Facet),如下图所示。你可能会记得我们在第二章:分析和修改数据中的经历,这样做并不有效,因为会出现太多的分类。对于OpenRefine来说,其会提示“总共有14,805个分类,数量超出了现实范围”。当然你可以通过点击Set choice count limit.来增加最大显示数,但是我们强烈建议你不要这么做。因为首先这可能导致OpenRefine运行变慢。其次,OpenRefine也只会直接列出多值分类内容(比如Hen eggs|Sectional models|Animal Samples and Products)。这无法让我们了解所有单独的分类内容,而我们感兴趣的恰恰在此。
为了解决这个问题,我们先不要关闭左侧透视窗口,选择Categories下拉菜单:Edit Cells | Split multi-valued cells…,如下图所示:
OpenRefine现在提示What separator currently separates the values?(分隔符是什么?)。我们可以从最初几行看出,值是被管道符分隔,也就是我们讲的垂直线。因此,我们在对话框中输入“|”。如果你在键盘中找不到这个符号,那也可以在单元格中复制然后粘贴到对话框中,然后点击OK.
几秒钟后,你可以看到OpenRefine已经分割好了单元格值,并且对Categories的透视界面也刷新了,显示了单独的分类。默认情况下是按照字母顺序显示的,如果我们按照频数显示的话我们能够获得更加有用的信息。我们可以将Sort by 选项从name改为count。这样我们就能够发现出现数最多的分类。
下面还需要做的是那些还没有变为单值的分类,我们需要将分类名称修改下,这样所有的行都会更新。比如,修改分类名Clothing and Dress,在透视界面中移动到该分类名上方,点击edit,如下图所示:
输入一个新的名称比如Clothing,然后点击Apply。OpenRefine 就会把所有Clothing and Dress名称修改为Clothing。并且透视界面也立即刷新了。
一旦你已经将分开的值编辑好了,那么你可以把他们重新组合在一起。点击Categories列的菜单:Edit cells |Join multi-valued cells…,然后输入你想要得分隔符。这次的分隔符并不一定要和原来的相同,有很多字符可以使用。比如,你可以使用逗号后面跟一个空格来做分隔符。
点2:行模式和记录模式的转换
现在让我们看下OpenRefine是如何处理多值单元格的。当我们按照上一点的操作步骤对一个列进行了分割后,我们发现OpenRefine做了两件事情。一方面,多值内容中的第一部分被替换放回原来的位置,另一方面,剩下的值被放到下一空行中对应的位置。举个例子,如下图所示,你可以看到ID7-ID9的记录基本是空行,只有Categories对应的单元格有内容,只有第一行(ID6)中其他单元格内有内容(ID6):
row是指数据集中的一行。 Record包括一个主体中的所有行。第一行所有单元格非空,标识一条记录;后续行中相同内容为空,表示这些行隶属于同一条记录 |
虽然这种处理方式避免了信息的重复和错误,但是也使得比较难分辨隶属于哪个主体。比如,如果我们对Categories列进行了文本透视(参照前一点),我们可以点击每个类别名称来看究竟有哪些行属于这个分类。但是,如果我们这么做的话,我们会发现许多空行:
产生上图结果的原因是:OpenRefine其实确实显示了所有分类值为Numismatics的行,这些行中包括那些Numismatics不是首个分类名称的行。但是对于某个主体中的其他行却并没有包括。这在我们关注某个主体中的所有行时就会产生问题。比如,我们可能想对所有类别为Numismatics的行进行标星操作,从而想对其进行后续操作时就会产生问题,我们可以试着这么做然后看看发生什么情况。
选中文本透视视图中的Numismatics,点击ALL下拉菜单中Edit rows | Star rows,然后点击文本透视视图中的reset来看看发生什么情况。我们发现只有值为Numismatics的行被标星了,而隶属于主体的其他行却并没有被标星。很显然我们丢失了信息。所以,让我们通过Undo / Redo标签页撤销标星操作。
OpenRefine可以让我们将隶属于同一个主体的所有行集合成一个单独的record(记录)。这样做的话,可以让我们在分割多值单元格的同时确保这些行还能够被认为是一个整体。我们可以在Show as 中将rows 改成records。你立即会发现行中颜色的改变。其会从以每个row进行颜色区隔变为以每个record进行颜色区隔。
如果我们在records模式中,在Categories透视图中选中Numismatics,我们可以发现包含Numismatics的所有主体都被选中了。如果我们通过ALL下的Edit
rows |Star rows进行标星,我们发现所有包含Numismatics的主体都被标星了。
以上说明,在records模式下,操作对整条记录有效,记录起码是一行以上。总结下,我们可以这么说,rows模式只是各个独立的行,而records模式则是一个整体,可以包含数行。
多参数下的记录匹配 如果你想匹配既在目录名称为Numismatics中又在目录名称Medals中的记录该怎么办呢?为了做到这点,首先请确保我们在records模式下,然后我们对Categories进行透视,首先我们选择Numismatics,然后再做一次透视,这次选择Medals,这样我们就获取到了我们想要的记录。 现在如果切换回rows模式会怎么样呢?突然,没有记录获得匹配。你起初可能感到疑惑,但其实很正常:没有一行是同时既等于Numismatics又等于Medals的,每一行最多只有这两项中的一项。因此,多重选择必须在records模式下。 |
另外请注意,本书其他章节请切换到rows模式,否则可能出错。如果出现不可预料的错误,请先检查下模式是否正确。这能减少很多麻烦。