Loading... <p style="margin-top: 0px;margin-bottom: 1.5em;padding-top: 0px;padding-bottom: 0px"> <hr /> <p style="margin-top: 0px;margin-bottom: 1.5em;padding-top: 0px;padding-bottom: 0px"><strong>本文原名</strong>“Don’t use Hadoop when your data isn’t that big ”<strong>,出自有着多年从业经验的数据科学家</strong>Chris Stucchio<strong>,纽约大学柯朗研究所博士后,搞过高频交易平台,当过创业公司的CTO,更习惯称自己为统计学者。对了,他现在自己创业,提供数据分析、推荐优化咨询服务,他的邮件是:stucchio@gmail.com 。</strong></p> <hr /> <p style="margin-top: 0px;margin-bottom: 1.5em;padding-top: 0px;padding-bottom: 0px"> 有人问我,“你在大数据和Hadoop方面有多少经验?”我告诉他们,我一直在使用Hadoop,但是很少处理几TB以上数据的任务 。我基本上只是一个大数据新手——知道概念,写过代码,但是没有大规模经验。</p> <p> 他们又问我,“你能使用Hadoop做简单的group by(<span style="font-family: Arial;font-size: 14px">分组)</span>和sum(统计)吗?”我说当然可以,但我会说需要看具体的文件格式。</p> <p>他们给我一个U盘,里面存储600MB数据(他们所有的数据,而不是样本数据)。不知道为什么,我用pandas.read_csv(Pandas是一种Python数据分析库)<span style="font-family: Arial;font-size: 14px">解决方案,</span>而不是Hadoop完成了这个任务后,他们显得很不满意。</p> <p> Hadoop实际上是有很多局限性的。Hadoop可以运行一个通用的计算,下面我用伪码进行说明:</p> <p>Scala风格的伪码:</p> <pre class="brush:python;toolbar:false">collection.flatMap( (k,v) => F(k,v) ).groupBy( _._1 ).map( _.reduce( (k,v) => G(k,v) ) )</pre> <p>使用SQL风格的伪码表示</p> <pre class="brush:python;toolbar:false">SELECT G(...) FROM table GROUP BY F(...)</pre> <p> 或者想我多年解释一样:</p> <pre class="brush:python;toolbar:false">目标:统计计算图书馆书籍的数量 Map:你统计奇数书架上书的数量,我统计偶数书架上书的数量。(做统计的人越多,统计出结果越快,就是机器越多,效率越高) Reduce:把我们每个人单独统计的结果数据加在一起。</pre> <p> 我们所做的只有两个:F(k,v)和G(k,v),除非要在中间步骤中做性能优化,其他一切都是固定的。</p> <p style="margin-top: 0px;margin-bottom: 18px;padding-top: 0px;padding-bottom: 0px;border: 0px;font-family: inherit;font-size: inherit;font-style: inherit;font-variant: inherit;font-weight: inherit;line-height: inherit;vertical-align: baseline"><span style="font-family: SimSun"> 在Hadoop里,所有计算都必须按照一个map、一个group by、一个aggregate或者这种计算序列来写。这和穿上紧身衣一样,多憋得慌啊。许多计算用其他模型其实更适合。穿上紧身衣(使用hadoop)的唯一原因就是,可以扩展到极大的数据集。可大多数情况,你的数据集很可能根本远远够不上那个数量级。</span></p> <p style="margin-top: 0px;margin-bottom: 18px;padding-top: 0px;padding-bottom: 0px;border: 0px;font-family: inherit;font-size: inherit;font-style: inherit;font-variant: inherit;font-weight: inherit;line-height: inherit;vertical-align: baseline"><span style="font-family: SimSun"> 可是呢,因为Hadoop和大数据是热词,世界有一半的人都想穿上紧身衣,即使他们实际不需要Hadoop。</span></p> <p><strong>一、如果我的数据量是几百兆,Excel可能没法加载它</strong><br /> 对于Excel来说的“很大的数据”并非大数据,其实还有其它极好的工具可以使用——我喜欢的是基于Numpy库之上Pandas。<span style="font-family: SimSun">它可以将几百MB数据以高效的向量化格式加载到内存,在我购买已3年的笔记本上,一眨眼的功夫,Numpy就能完成1亿次浮点计算。Matlab和R也是极好的工具。</span></p> <p> Pandas构建于Numpy库之上,可以以矢量格式的方式有效地把数百兆的数据载入到内存中。在我购买已3年的笔记本上,它可以用Numpy在一眨眼的功夫把1亿的浮点数乘在一起。Matlab和R也是极好的工具。<br /> 因此,对于几百兆的数据量,典型的做法是写一个简单的Python脚本逐行读取,处理,然后写到了一个文件就行了</p> <p><strong>二、可我的数据是10GB呢?</strong><br /> <span style="font-family: SimSun">我买了台新笔记本,它有16GB的内存(花$141.98)和256GB的SSD(额外200美元)。,如果在Pandas里加载一个10GB的csv文件,实际在内存里并没有那么大(内存不是占有10G)——可以将 “17284932583” 这样的数值串存为4位或者8位整数,“284572452.2435723”存为8位双精度。</span></p> <p><span style="font-family: SimSun"> 最坏的情况下你还可以不同时将所有数据都一次加载到内存里。</span></p> <p><strong>三、可我的数据是100GB、500GB或1TB呢?</strong></p> <p><span style="font-family: SimSun"> 一个2T的硬盘才94.99美元,4T是169.99。买一块,加到桌面PC或者服务器上,然后装上PostgreSQL来解决它</span></p> <p><strong>四、Hadoop << SQL或Python脚本</strong></p> <p> 在计算的表达能力来说,Hadoop比SQL差。Hadoop里能写的计算,在SQL或者简单的Python脚本都可以更轻松地写出来。<br /> <span style="font-family: SimSun"> SQL是一个直观的查询语言,适合做业务分析,业务分析师和程序员都很常用。SQL查询非常简单,而且还非常快——只有数据库使用了正确的索引,要花几秒钟的sql查询都不太常见。</span></p> <p><span style="font-family: SimSun"> Hadoop没有索引的概念,Hadoop只有全表扫描,而且Hadoop抽象层次太多了——我之前的项目尽在应付Java内存错误( java memory errors)、内存碎片和集群竞用了,而这些时间远多于实际的数据分析工作。</span></p> <p><span style="font-family: SimSun"> 如果你的数据并不是像SQL表那样的结构化数据(比如纯文本、JSON对象、二进制对象),通常是直接写一个小的Python脚本或者Ruby脚本逐行处理更直接。保存到多个文件,然后逐个处理即可,SQL不适用的情况下,从编程来说Hadoop也没那么糟糕,但相比Python脚本仍然没有什么优势。</span></p> <p><span style="font-family: SimSun"> 除了难以编程,Hadoop还一般总是比其他技术方案要慢。只要索引用得好,SQL查询非常快。比如要计算join,PostgreSQL只需查看索引(如果有),然后查询所需的每个键。而Hadoop呢,必须做全表扫描,然后重排整个表。排序通过多台机器之间分片可以加速,但也带来了跨多机数据流处理的开销。如果要处理二进制文件,Hadoop必须反复访问namenode。而简单的Python脚本只要反复访问文件系统即可。</span></p> <p><strong>五、我的数据超过了5TB</strong></p> <p><span style="font-family: SimSun"> 只能使用Hadoop,而无需做过多的选择。<br /></span></p> <p><span style="font-family: SimSun"> 你的命可真苦——只能苦逼地折腾Hadoop了,没有太多其他选择(可能还能用许多硬盘容量的高富帅机器来扛),而且其他选择往往贵得要命(脑海中浮现出IOE等等字样……)。</span></p> <p><span style="font-family: SimSun"> 用Hadoop唯一的好处是扩展。如果你的数据是一个数TB的单表,那么全表扫描是Hadoop的强项。此外的话(如果你没有这样大数据量的表),请关爱生命,尽量远离Hadoop。它带来的烦恼根本不值,用传统方法既省时又省力。</span></p> <p><strong>六、Hadoop是一个极好的工具</strong></p> <p> 我并不讨厌Hadoop,当我用其它工具不能很好处理数据时我会选择Hadoop。另外,我推荐使用Scalding,不要使用Hive或Pig。Scalding支持使用Scala语言来编写Hadoop任务链,隐藏了其下的MapReduce。</p> 最后修改:2021 年 12 月 10 日 10 : 53 AM © 允许规范转载 赞赏 如果觉得我的文章对你有用,请随意赞赏 赞赏作者 支付宝微信