根据我做项目的经验,我来做项目。首先我分析了项目的目的和需求,了解了这个项目属于什么问题,想要达到什么效果。然后提取数据,做基本的数据清洗。第三步是特征工程,这是个脏活,耗费大量精力。如果特征工程做得好,后面选择哪种算法其实差别不大。反之,无论选择什么算法,效果都不会有突破性的提升。第四步,运行算法。通常我会先运行所有能运行的算法,看效果,分析预判/召回和f1-score,看有没有异常(比如有几个算法精度特别好,但是召回特别低,需要从数据上找原因,或者从算法上看算法是否不适合这个数据)。如果没有异常,则进行下一步。调谐方法有很多,如网格搜索、随机搜索等。用于调整参数,并根据具体数据和场景进行具体分析,以调整性能。调优后,运行算法,看看结果是否有所改善。如果没有,找到原因。数据还是算法?是数据质量不好,特性问题还是算法问题。一个一个查,想办法解决。问题会回到特征工程前的第三步,数据质量问题会回到第一步,看数据清洗有没有遗漏,异常值有没有影响算法的结果。算法问题会回到第四步,看看算法流程的哪一步出了问题。如果没有工作,可以搜索相关论文,看看里面有没有解决的办法。这样重复几次,就可以得到结果了。写技术文档和分析报告,然后向业务人员或产品说明我们做了什么。然后他们会提出建议/要求,不断循环。最后,代码将上线,bug将被纠正,直到项目被关闭。
直观上,它可以用一个流程图来表示:
今天,我们来谈谈数据清理。为什么我们需要数据清理?我们在书上看到的数据,比如常见的虹膜数据集、房价数据集、电影评分数据集等。是高质量的,没有缺失值、异常点和噪声。在真实数据中,我们得到的数据可能包含大量的缺失值、大量的噪声,或者由于人工输入错误而产生的异常点,这些都给我们挖掘有效信息带来了一定的麻烦。所以,我们需要通过一些方法来尽力。数据清理通常包括以下步骤:
一.数据分析
二。缺失值的处理
三。异常值的处理
四。去后处理
动词(verb的缩写)噪声数据处理
不及物动词一些实用的数据处理工具
一.数据分析
在实际项目中,我们在确定需求时,会寻找相应的数据。我们拿到数据后,首先要对数据进行描述性统计分析,看看哪些数据不合理,也可以知道数据的基本情况。如果是销售数据,可以通过分析销售总额、人均消费、人均消费次数等来了解数据的基本情况。不同商品的消费金额,同一商品在不同时间的消费金额和消费频率。此外,我们可以了解数据的质量,是否有异常点,噪音等。通过画画。比如(这里数据较少,可以直接用R作图):
#年薪十万元以上的一群管理者的收入薪酬=C (11,19,14,22,14,28,13,81,12,43,11,16,31,16,23.42,22,26,17,22,13,27 14,17,13,38,28,40,85,32,25,26,16,12
从上面四个数字可以清楚的看出,180是一个异常值,也就是第23个数据需要清理。
Python还包含了大量的统计命令,其中主要的统计特征函数如下图所示:
二。缺失值的处理
缺失值是实际数据中不可避免的问题。有的人直接删除缺失的数据,有的人直接给它0值或者特殊值。那么我们该怎么办呢?不同的数据场景应该采用不同的策略。首先,应该判断缺失值的分布:
1导入scipy作为sp 2 data=sp . genfromtx(web _ traffic.tsv ,分隔符=\ t )
数据如下:
数据数组([[1.000000000 e 00,2.272000000 e 03],[ 2.00000000e 00,nan],[3.000000000 e 00,1.38600000e 03),[7.410000000 e 02,5.3920000000 e 03],[7.4200000000 e 02,5.906000000 e 03],[7.430000000 e 02,4.8810000000 e 03]])打印数据[:10][[1.00000000000 e 00 2.27200000003][2.0000000]
如您所见,第2列中出现了缺失值。现在让让我们看看缺失值的数量:
1 x=data[:0] 2 y=data[:1] 3 sp.sum(sp.isnan(y)) 4 8
在743个数据中,只有8个数据丢失,因此删除它们对整体数据情况的影响很小。当然这是在缺失值很少的情况下,缺失值很多的情况下,这个维度的信息还是很重要的(因为如果缺失值占95%以上,这个维度的数据可以直接删除),直接删除会对后面的算法结果产生不好的影响。我们通常使用以下方法:
1.直接删除——适用于缺失值数量少且随机出现,删除对整体数据影响不大的情况。
2.用全局常数填充——例如,用未知,但效果不一定好,因为算法可能会把它识别为一个新的类别,很少使用。
3.用均值或中位数代替——优点:不会减少样本信息,处理简单。缺点:当缺失数据不是随机数据时,会出现偏差。对于正态分布的数据,可以用均值代替。如果数据有偏差,使用中位数可能更好。
4.插值法
1)随机内插法——从总体中随机选取一个样本来代替缺失样本。
2)多重插值法——通过变量之间的关系预测缺失数据,用蒙特卡罗方法生成多个完整的数据集,对这些数据集进行分析,最后汇总分析结果。
3)热平台插值——指在非缺失数据集中寻找与缺失值相似的样本(匹配样本),利用观测值对缺失值进行插值。
优点:操作简单易行,准确率高。
缺点:当变量较多时,通常很难找到与待插值样本完全相同的样本。但我们可以根据一些变量将数据分层,对层内缺失值进行均值插值。
4)拉格朗日差分法和牛顿插值法(简单高效,数值分析中的内容,数学公式待后补充==)
5.建模方法
它可以通过回归、使用贝叶斯形式方法的基于推理的工具或决策树来推断和确定。例如,使用数据集中其他数据的属性,可以构建决策树来预测缺失值的值。
以上方法各有利弊,应根据实际数据分布、倾斜程度、缺失值比例等情况选择方法。一般来说,建模法是一种常用的方法,根据已有值预测缺失值,精度较高。
三。异常值的处理
离群值通常被称为离群值。在谈到分析数据时,我们举一个例子来说明如何发现异常值。除了画图(画图不常用,因为数据量大的时候画图很难很慢),还有很多其他方法:
1.简单统计分析
获得数据后,您可以对数据执行简单的描述性统计分析。比如可以用最大值和最小值来判断这个变量的值是否超出合理范围。比如客户的年龄是-20或者200岁,这显然是不理智的,不正常的。
在python中可以直接使用熊猫的describe():
将熊猫导入为PD data=PD . read _ table(web _ traffic.tsv ,header=None) data.describe() 0 1计数743.0000000 735.000000平均值372.0000000 1962.165986 STD 214.629914 860.720997min 1.000000 472.000000 25% 186.500000 1391.00000 50% 372.00
2.3原则
如果数据服从正态分布,在3的原则下,异常值是一组测量值中,与平均值的偏差超过3倍标准差的值。如果数据服从正态分布,则平均值3以外的值出现的概率为P (| x-u | 3)=0.003,属于罕见的小概率事件。如果数据不服从正态分布,也可以用标准差偏离平均值多少倍来描述。
3.箱线图分析
箱线图提供了一个识别异常值的标准:如果一个值小于QL01.5IQR或大于OU-1.5IQR,则称为异常值。QL是下四分位数,这意味着所有观测值的四分之一比它小;QU是上四分位数,表示所有观测值的四分之一大于它;Iq是四分位间距,即上四分位QU和下四分位之差,包含所有观察值的一半。用箱线图判断异常值的方法是基于四分位数和四分位数距离,四分位数是稳健的:25%的数据可以变得任意远,不会干扰四分位数,所以异常值可以不要影响这个标准。因此,盒图在识别异常值方面是客观的,在识别异常值方面具有一定的优势。
4.基于模型的检测
首先建立一个数据模型,异常是那些不能与模型完美拟合的对象。如果模型是一组群集,则例外是不明显属于任何群集的对象;当使用回归模型时,例外是相对远离预测值的对象。
优缺点:1。有了坚实的统计理论基础,当有足够的数据和所用测试类型的知识时,这些测试可能非常有效;2.对于多元数据,可用的选择较少,对于高维数据,这些检测可能性很差。
5.基于距离的
通常可以在对象之间定义邻近度,异常对象是那些远离其他对象的对象。
优缺点:1。简单;2.缺点:基于接近度的方法需要O(m2)时间,大数据集不适合;3.这种方法对参数的选择也很敏感;4.具有不同密度区域的数据集可以被处理,因为它使用一个全局阈值,可以不要考虑这种密度变化。
6.基于密度
当一个点的局部密度明显低于其大多数邻居的密度时,该点被归类为异常值。适合不均匀分布的数据。
优缺点:1。它给出了对象是离群点的定量度量,即使数据有不同的区域也能很好的处理;2.像基于距离的方法一样,这些方法必须具有O(m2)的时间复杂度。O (mlogm)可以通过对低维数据使用特定的数据结构来实现;3.很难选择参数。虽然算法通过观察不同的K值并获得最大离群值得分来处理这个问题,但仍然需要选择这些值的上下限。
7.基于聚类:
基于聚类的离群值:如果一个对象不属于任何聚类,则它是基于聚类的离群值。离群点对初始聚类的影响:如果聚类检测到离群点,就有一个问题:因为离群点影响聚类,所以结构是否有效。为了处理这个问题,可以使用以下方法:对对象进行聚类,删除离群点,重新对对象进行聚类(这不能保证得到最好的结果)。
优缺点:1。基于线性和近似线性复杂度(K-means)的聚类技术对于发现异常值可能非常有效;2.聚类的定义通常是离群值的补充,因此既可以发现聚类也可以发现离群值;3.所生成的离群值集合及其分数可能取决于所使用的聚类数量以及数据中离群值的存在;4.聚类算法生成的簇的质量对该算法生成的离群点的质量有很大影响。
处理方法:
1.删除异常值——很明显是异常的,而且数量很少,可以直接删除。
2.不处理——如果算法对离群点不敏感,可以不处理,但是如果算法对离群点敏感,最好不要用,比如一些基于距离计算的算法,包括kmeans,knn之类的。
3.平均值替代——损失信息小,简单高效。
4.视为缺失值——可以按照缺失值的处理方法进行处理。
四。去后处理
以DataFrame数据格式为例:
#创建数据,其中包含重复数据data data=PD . data frame({ v1 : ['一] * 5 ['b ] * 4,'v2 :[1,2,2,3,4,4,5,3]})data v1 V20A 11A 22A 23A 24a 35 b46 b47 b 58 B3 # Dataframe的duplicated方法返回一个布尔型序列,指示每一行是否是重复的行data . duplicated()0 false 1 false 2 true 3 true 4 false 5 false 6 true 7 false 8 false DType:bool # drop _ duplicates方法用于返回data frame数据。删除了重复行的drop _ duplicates()v1 v 20 a 1a 2 a 24 a 35 b 47 b 58 b 3 #。这两种方法默认会判断所有列,也可以指定一些列来判断重复。假设您仍然有一个值列表,并且您只想根据v1列:data[v3 ]=range(9)data v1 v2 v3 0 a 101 a 22 a 23 a 234 a 345 b 456 b 467 b 578 b 38 data。drop _ duplicates([v1 ])默认情况下,V2V30A105B45 # duplicated和drop_duplicates保留值的第一个组合。如果传入的take_last=True,则保留最后一个:data . drop _ duplicates([v1 ,'v2 ],take _ last=true)v1 v2 v3 0 a 103 a 234 a 346 b 467 b 578 b 38。
如果数据是列表格式,有几种方法可以删除它
0=['b ,'c ,'d ,'b ,'c ,'一'一]方法一:使用set() list1=sorted(set(list0),Key=list 0 . index)# sorted output print(list 1)方法二:使用{}。fromkeys()。keys () list2={}。fromkeys(列表0)。keys () print (list2)方法三:set()sort()3=list(set(list 0))list 3 . sort(key=list 0 . index)print(list 3)方法四:iterate list 4=[]for I in list 0:if not I in list 4:list 4 . append(I)print(list 4)方法五:排序后比较相邻两个元素的数据,删除def sort list(list 0):list 0 . sort()last=list 0[-1]for I in range(len(list 0)-2,-1,-1): if
动词(verb的缩写)噪音处理
噪声是被测变量的随机误差或方差。我们上面提到过离群值(outliers),那么离群值和噪声是一回事吗?我们知道,测量)=真实数据噪声。离群值属于观测值,可能是真实数据或噪声造成的,但一般来说,与大多数观测值有明显的不同。包括偏离预期的噪声误差值或异常值,但是它可以不能说噪声点包含离群值,尽管大多数数据挖掘方法将离群值视为噪声或异常并将其丢弃。但是,在一些应用中(如欺诈检测),会对异常值进行异常值分析或异常挖掘。而且有些点在局部属于异常值,但从全局来看是正常的。
我在quora上看到一个有趣的例子来解释噪音和离群值:
离群值:你一丝不苟地列举你所拥有的一切。你发现了3个10美分硬币,1个25美分硬币,哇,一张100美元的钞票,你上次买酒的时候把它放在那里了,后来完全忘了。100美元钞票是一个离群值,因为它一般不会放在口袋里。
噪音:你刚从那个俱乐部回来,喝得烂醉如泥。你试图找到一些钱买些东西来醒酒,但是你很难正确地读出硬币上的数字。你发现了3个1角5分的硬币,哇,一张100美元的钞票。但事实上,你把25美分的硬币错当成了10美分的硬币:这个错误在你所访问的数据中引入了噪音。
换句话说,数据=真实信号噪声。离群值是数据的一部分。
翻译过来就是:
离群值:你正在用尽你口袋里的钱,你发现三个一角,一个五角和一张毛爷爷的照片从100元对你微笑。这100元是一个离群值,因为它不应该不要总是出现在口袋里。
噪音:你晚上去了三里屯,喝得很醉。你需要买些东西来清醒一下。这时,你开始翻口袋里的零钱包。嗯,你找到了三个一角的,一个五角的,还有一张100元的毛爷爷对你微笑的照片。但是突然之间,你就晕了,把那三个角当成了三个1元.这种错误的判断使得数据集中出现了噪声。
那么我们应该如何应对噪音呢?有几种方法:
1.分箱法
宁滨方法通过检查邻居(即周围的值)。这些有序值被分布到一些水桶或者垃圾箱。因为宁滨方法检查最近邻的值,所以它执行局部平滑。
使用条柱平均值平滑:条柱中的每个值都被条柱平均值替换。
使用框中值平滑:框中的每个值都被框中的中值替换。
用盒子边界平滑:盒子中的最大值和最小值也被视为边界。容器中的每个值都被最近的边界值替换。
一般来说,宽度越大,平滑效果越明显。框也可以等宽,其中每个框值的间隔范围是常数。分箱也可以作为一种分立技术。
2.回归方法
您可以使用函数来拟合数据以平滑数据。线性回归包括寻找最佳拟合两个属性(或变量)的直线,以便一个属性可以预测另一个属性。多元线性回归是线性回归的扩展,涉及两个以上的属性,数据拟合到一个多维面上。利用回归找到适合数据的数学方程,有助于消除噪声。
不及物动词一些实用的数据处理工具
1.删除文件中多余的空行。
空白主要指(\n,\r,\r\n,\n\r等。).在python中,有一个strip()的方法,可以去掉多余的空白在绳子的两端。这里的空格主要包括空格、制表符(\t)和换行符。但是经过近距离测试,我们发现strip()可以匹配\n、\r\n、\n\r等。但可以过滤掉个人\r为了万无一失,我还是喜欢用麻烦的方法,如下:
#-*-编码:utf-8 -*- #文本格式化处理,过滤掉空行file=open(123.txt )I=0而1: line=file.readline()。strip()如果不是line:break I=i1line 1=line . replace(\ r , '')f1=打开(filename.txt ,'一)f1 . write(line 1 \ n )f1.close()打印字符串(I)
2.如何判断文件编码格式?
#-*-编码:utf8 -*- #批处理编码格式转换(优化)导入OS导入chardet path1=e://2016 utf/def dirlist(path):file list=OS . listdir(path)for filelist:file path=OS . path . join(path,filename)if OS . path . is dir(file path):dirlist(file path)else:if file path . ends with(xt ):f=open(file path)data=f . read()if chardet . detect(data)[编码] !='utf-8 打印文件路径- 'chardet . detect(data)[编码]目录列表(路径1)
3.文件编码格式转换,gbk和utf-8之间的转换
这主要是因为当对文件编码格式有特殊要求时,需要批量将文件从gbk转换为utf-8或utf-8转换为gbk编码格式。
#-*-编码:gbk -*- #批量处理编码格式转换导入编解码器导入操作系统路径1=e://dir/def ReadFile(文件路径,编码=utf-8 ):带编解码器。打开(文件路径,r ,编码)为f:返回f . read()def WriteFile(文件路径,u,编码=gbk ):带编解码器。打开(文件路径,w ,编码)为f:f . write(u)def UTF8 _ 2 _ GBK(src,dst): content=ReadFile(src,编码=utf-8 )WriteFile(dst,content,encodingtxt ):打印文件路径# OS。重命名(文件路径,file path . replace(xt ,'doc ))try: UTF8_2_GBK(filepath,filepath)异常,ex:f=open(error.txt ,'一)f . write(文件路径\ n )f . close()目录列表(路径1)
刚写完比较粗糙,以后会不断修改。下篇写数据转换方面的内容,包括标准化,归一化正则化等。如果有错误,欢迎指正!
标签:数据值方法