使用mrjob简单的编写mapreduce模型的程序

    这次主要简单的分享下mapreduce编程模型,mapreduce作为分布式计算模型中最流行的一种,自从由google的论文发布这一模型之后,就受到了很多人的追捧,这次我们也跟随一下潮流。为了不让大家看着头晕,我不打算直接用hadoop(由java编写的mr模型的实现),而是采用python一个简单的实现来操作。

     本着简单的原则,我们从最经典的一个例子wordcount来讲解。wordcount顾名思义,就是单词统计,即统计一段文本中所有出现的单词次数(单词频率)。肯定有人看了不屑一顾是吧,认为单词统计有什么意思,但是小小的单词统计其实是可以引申到很多应用的,比如在商场的销售物品清单中,计算出不同商品的销售量,以便做更好的促销政策,比如在一个网站的web访问日志中,统计不同的页面的访问量,以便运营人员做更好的页面优化,总之以点到。
     ok,我们先来一个常见的单词统计,你们会想到用什么来做呢,key-value的字典结构肯定是第一个想到的。

	import re
	WORD_RE = re.compile(r"[\w']+") #分割单词的正则
	st = """
		Today our fellow citizens our way of life our very freedom came under attack 
		in a series of deliberate and deadly terrorist acts The victims were in airplanes 
		or in their offices Secretaries business men and women military and federal 
		workers Moms and dads Friends and neighbors
		"""

	wordList = WORD_RE.findall(st)
	countDic = {}
	for x in wordList:
		countDic.setdefault(x,0)
		count = countDic[x]
		countDic[x] = count+1
	print countDic



     简简单单的一段文字就是用来统计单词的次数的,但是想过没有,如果文本很大的话会怎样。你一个字典放得下去吗?1T的文本,你的字典可以放得下吗?没错,分布式计算的使用场景就是在大数据方面,这个时候需要mapreduce登场了。
     MapReduce用于大规模数据集(大于1TB)的并行运算。概念"Map(映射)"和"Reduce(归约)",和他们的主要思想,都是从函数式编程语言里借来的,还有从矢量编程语言里借来的特性。他极大地方便了编程人员在不会分布式并行编程的情况下,将自己的程序运行在分布式系统上。当前的软件实现是指定一个Map(映射)函数,用来把一组键值对映射成一组新的键值对,指定并发的Reduce(归约)函数,用来保证所有映射的键值对中的每一个共享相同的键组。
     MapReduce通过把对数据集的大规模操作分发给网络上的每个节点实现可靠性;每个节点会周期性的返回它所完成的工作和最新的状态。如果一个节点保持沉默超过一个预设的时间间隔,主节点(类同Google File System中的主服务器)记录下这个节点状态为死亡,并把分配给这个节点的数据发到别的节点。每个操作使用命名文件的原子操作以确保不会发生并行线程间的冲突;当文件被改名的时候,系统可能会把他们复制到任务名以外的另一个名字上去。(避免副作用)。
     化简操作工作方式与之类似,但是由于化简操作的可并行性相对较差,主节点会尽量把化简操作只分配在一个节点上,或者离需要操作的数据尽可能近的节点上;这个特性可以满足Google的需求,因为他们有足够的带宽,他们的内部网络没有那么多的机器。总而言之,mapreduce属于计算机相互间的并行计算,我们借助mapreduce的编程模型框架,可以忽略底层的数据交互还有分工协作,假设在机器资源足够的情况下,我们只要横向的部署程序到其他机器上,就可以增加程序的计算能力,不需要我们去关注底层的细节。

     我上面说过我为了让大家看起来不会晕,在这里只是进行简单的讲解,我们关注的是mapreduce的编程模型,不打算去关注服务器如何去部署这些分布式的程序,也不打算用hadoop来实现这个wordcount程序,而是用python中比较小巧的一个框架 mrjob 来简单的实现上面的说到的mapreduce程序。

     

from mrjob.job import MRJob
import re

WORD_RE = re.compile(r"[\w']+")

class MRMostUsedWord(MRJob):
    def mapper_get_words(self, _, line):
        # yield each word in the line
        for word in WORD_RE.findall(line):
            yield (word.lower(), 1)
		
    def reducer_count_words(self, word, counts):
        # send all (num_occurrences, word) pairs to the same reducer.
        # num_occurrences is so we can easily use Python's max() function.
        yield (word,sum(counts))
	def steps(self):
			return [
				self.mr(mapper=self.mapper_get_words,
						combiner=self.combiner_count_words,
						reducer=self.reducer_count_words),
			]

if __name__ == '__main__':
    MRMostUsedWord.run()
	


 
运行只需要用 下面的就可以执行了
python my_job.py < input.txt

     简单的讲解下这个程序,mapreduce主要是关注map函数还有reduce函数,map函数作为程序的输入,会由框架按照数据分布输入计算好的部分内容,也就是上面内容中的line参数,这个就是由mapreduce编程模型来自动输入内容供我们计算,map函数的输出值是一个(Key,value)的返回值,等等我在讲解下这个key-value的返回值有什么用。
     reduce才是真正的输出结果的函数,在reduce中,会接收到所有的key以及value,当然这个key是上面map函数输出的key,然而,value却不是
上面map函数的输出的value,这里的value是指相同的key合并加起来的值,比如 两个and  对应的value就是2。
     ok,简单的mapreduce的分享就到这里,希望可以一起学习探讨。

 

 

 


 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值