Hadoop - 分析日志文件(Java)

6

日志文件的格式如下:

Time stamp,activity,-,User,-,id,-,data

--

2013-01-08T16:21:35.561+0100,reminder,-,User1234,-,131235467,-,-
2013-01-02T15:57:24.024+0100,order,-,User1234,-,-,-,{items:[{"prd":"131235467","count": 5, "amount": 11.6},{"prd": "13123545", "count": 1, "amount": 55.99}], oid: 5556}
2013-01-08T16:21:35.561+0100,login,-,User45687,-,143435467,-,-
2013-01-08T16:21:35.561+0100,reminder,-,User45687,-,143435467,-,-
2013-01-08T16:21:35.561+0100,order,-,User45687,-,-,-,{items:[{"prd":"1315467","count": 5, "amount": 11.6},{"prd": "133545", "count": 1, "amount": 55.99}], oid: 5556}
...
...

编辑

这个日志的具体例子:

User1234收到了一个提醒 - 这个提醒id131235467,之后他下了一个订单,订单的数据如下:{items:[{"prd":"131235467","count": 5, "amount": 11.6},{"prd": "13123545", "count": 1, "amount": 55.99}], oid: 5556} 在这种情况下,idprd的值相同,所以我要计算count*amount的总和 -> 在这个例子中,5*11.6 = 58,输出结果为

User 1234    Prdsum: 58    

User45687 也下了一笔订单,但他没有收到提醒,因此他的 data 没有被总结。

User45687    Prdsum: 0

这个日志的最终输出结果:

User 1234    Prdsum: 58    
User45687    Prdsum: 0

我的问题是:如何在data中比较这些值 -> idprd?关键是用户。是否可以使用自定义的Writable -> value = (id,数据)?我需要一些想法。

什么是问题? - Gilbert Le Blanc
2个回答

0

我建议像你现在这样获取原始输出总和,作为一个Hadoop作业的第一次通过的结果,这样在Hadoop作业结束时,你就会得到这样的结果:

User1234     Prdsum: 58    
User45687    Prdsum: 0

然后再有第二个Hadoop作业(或独立作业)来比较各种值并生成另一个报告。

你需要在第一个Hadoop作业中包含“状态”吗?如果是这样,那么你需要在mapper或reducer中保留一个HashMap或HashTable,用于存储所有键(在这种情况下为用户)的值以进行比较 - 但我认为这不是一个好的设置。最好在一个Hadoop作业中进行聚合,并在另一个作业中进行比较。


User1234有一个包含2个产品的订单,因此当我汇总输出时,a) {"prd":"131235467","count": 5, "amount": 11.6} --> 511,6 = 58 和 b) {"prd": "13123545", "count": 1, "amount": 55.99} --> 155,99 = 55,99。但我只对a)感兴趣,因为a的prd等于reminder的id。当我在第一个任务中进行原始输出求和时,如何区分第二个任务中我要查找的那个总和(reminder.id == data.prd)?或者我是否误解了您的答案? - JustTheAverageGirl

0

实现的一种方法是使用复合键。 Mapper输出键是userid和event id(提醒-> 0,订单-> 1)的组合。使用userid分区数据,并需要编写自己的比较器。 以下是要点。

Mapper

for every event check the event type 
    if event type is "reminder"
        emit : <User1234,0> <reminder id>
    if event type is "order"
        split if you have multiple orders
        for every order
            emit : <User1234,1> <prd, count* amount, other interested blah>

使用用户ID进行分区,以便所有具有相同用户的条目都将进入同一个Reducer。

Reducer

在Reducer中,所有条目将按用户ID分组并按事件ID排序(即首先获取给定用户ID的所有提醒,然后是订单)。

If `eventid` is 0
    add reminders id to a set (`reminderSet`).

If `eventid` is is 1 &&  prd is in `remindersSet` 
   emit : `<userid>  <prdsum>`
else 
   emit : `<userid>  <0>` 

有关复合键的更多详细信息可以在“Hadoop权威指南”或此处找到。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接