recordreader,recordwriter方法都是对每一个key,value进行的,只不过一个是读,一个是写;
两者都要从format开始,分别是inputformat和outputformat,对于recordreader是从分片里读取的数据,分片也有格式,当然也可以重写,因为有个抽象类inputsplit,输入内容也是通过文件流读取,这个流实际上也是可以重写和重定向的,所以数据来源,根据不同的格式,不同的内容,可以进行不同的封装使用,然后是recordreader,将其作为参数放入context中,主要使用nextkey,value来读取分片;然后使用map函数做循环运算;outputformat则是使用的是recordwriter,这个也是一个抽象类,可以自己实现自定义的东西,用来将东西写出去,可以将其结果接到不同的流,来读到不同的地方;
分组,则是在reduceTask端的一个聚合步骤的子过程,要将每个map中属于自己的partitioner的部分取出,除了对partitionId进行比较之外,还有对于key的排序;排序之后是合并相同key的keyvalue,将value作成list,list也是要排序的,通过重写key的识别,来将不同的keyvalue来达到分组效果,结果只保留最后一个key,或者自己定义key形式;分块,则在maptask端就进行了,当进行了spill(溢出)操作结束,要对相同partitionId的spil进行合并;然后按照partition排序,再按key排序,在此时,排序的是元数据(在合并之前),对元数据进行排序,然后合并,删除原来的小spill;对分组操作,其实也是个比较key的结果,所以也可以通过重写比较来定义分组;