相信任何一位数据专业人士都会认同:实现高数据质量的最大障碍之一就是数据清洗。换句话说,我们应该从其他可用的数据集中删除不准确或不具代表性的数据。根据数据类型和数据处理状态以及数据产品开发的不同,数据清洗也有多种形式。
正如我们刚刚看到的传感器,入口点的数据不太可能是干净的。毕竟,你的数据只是从混乱的外部世界中获得的。这其中难免会有遗漏、错误信息、极端值和不兼容的格式,但通过正确的数据清洗方法,这些问题都能被轻松避免。数据清洗是业内最近引起关注的一个领域,尤其是在机器学习方面。我们已经花费了很多精力来决定如何正确地进行数据清洗。下面探讨了一些清洗数据的常见方式,以及在每种情况下你可以执行哪些操作。
异常值去除
这个世界很嘈杂,所以你的数据也会很嘈杂。但太过嘈杂的数据通常会导致机器学习管道失效或者让业务仪表板看起来非常不准确。在某些情况下,你会希望尽早从数据中识别并删除异常值。当然,如果你的下游任务就是异常值检测的话,那就没有意义了。不过想想与传感器数据类似的情况,正常来说一个99999°的温度读数可能不应该被直接传递。你可以考虑用标准分数等统计技术( https://oreil.ly/N60ol )或更新潮的算法技术[如孤立森林( https://oreil.ly/J9kTW )]来去除异常值。如果你的数据集很大,请特别注意检测过程的时间复杂度。我们将在第5章就异常检测进行深入讨论。
评估数据集特征
看看你收集到的数据的结构,这些数据都和你的最终目标相关吗(即便只是弱相关)?正如我们讨论的HTTP状态码一样,有时数据的整个部分都与下游任务无关,那么你应该把它们清洗出去!诚然,云存储的成本正在下降,但存储无意义的数据不仅是一个存储问题,其他工程师也可能对为什么会存在某个字段而感到困惑。通常来说,更多的特征意味着需要更多的文档或更多的领域知识来理解你的系统,而这两者都会让你的分析复杂化,并影响数据质量。你要认真思考数据集的哪些特征才是解决问题所必需的。
数据归一化
有些数据点可以单独检查,这没有问题。但其他数据在与相同类型的数据进行比较时才是最有意义的。在这些情况下,在清洗或转换步骤期间对数据进行归一化通常可以帮助到你和你的机器学习系统。归一化常用的选择包括:L1范数(曼哈顿距离, https://oreil.ly/0zwO2 )、L2范数( https://oreil.ly/BOhNm )、去均值化( https://oreil.ly/mMk3D )和单位方差( https://oreil.ly/aY8Cy ),而最佳选择将取决于数据的用例。
数据重建/数据重构
有时,你收集到的数据中的某些字段会丢失。这会发生在容易出错的API调用或传感器可能离线等情况下。在许多例子中,这种遗漏是可以的,但有时你可能需要所有字段都具有与它们相关联的值。在这些情况下,通常可以使用插值法( https://oreil.ly/AJFGz )、外推法( https://oreil.ly/FsNTx )或对相似数据进行分类/标记( https://oreil.ly/sAwB3 )来填补缺失值,即便数据伴随一点噪声也无妨。
时区转换
你可能会将时区转换视为一种归一化。但这一步对于许多数据清洗任务来说都非常重要,所以时区转换值得单独一提。你的应用程序用户或传感器可能遍布全球,这意味着它们将记录不同的本地时间戳。只有在某些相同的标准下,才能将时间戳相互比较。我们通常会使用协调世界时(Coordinated Universal Time,UTC)。UTC不是时区,而是时间标准,使用格林尼治标准时间(Greenwich Mean Time,GMT)的国家碰巧总是与UTC一致,但这些国家并不使用UTC。如果你不进行时区转换,并且疯狂到在收集时不捕获时区信息,那么你将永远无法知道两个国际事件相对彼此发生的先后顺序。此外,许多软件错误可以追溯到时区混乱(“千年虫”可能是其中最著名的例子),因此请仔细检查你的时区,以确保它们按照UTC标准来转换或捕获时间。
类型强制转换
大多数结构化数据都是类型化的,这意味着它必须遵循某种格式。在计算中,我们经常需要模糊这些格式之间的界限,以便让应用程序正常运行。例如,浮点数可能会被截断为整数,字符可能会变成字符串等。如果下游应用程序需要某种类型的数据,你需要考虑强制对其进行转换。换句话说,作为数据清洗过程的一部分,你需要将值从一种数据类型自动或隐式转换为另一种数据类型。如果要组合来自不同格式的数据,类型强制转换也是不可或缺的。许多库和应用程序对不同的事物都有自己的数据类型,并且通常需要将它们显式转换为新的、更容易接受的格式。
清洗数据的方法列表还在继续完善,你也应该经常对其进行补充。接下来是数据处理。