Hadoop Reducer 自定义可写
Hadoop Reducer Custom Writable
我有以下 Reducer class
public class CompanyMinMaxReducer extends Reducer<Text, DateClosePair, Text, Text> {
private Text rText = new Text();
public void reduce(Text key, Iterable<DateClosePair> values, Context context)
throws IOException, InterruptedException {
int min = Integer.MAX_VALUE;
int max = Integer.MIN_VALUE;
LongWritable minDay = new LongWritable();
LongWritable maxDay = new LongWritable();
for(DateClosePair val: values){
LongWritable tempDate = val.getDate();
DoubleWritable tempClose = val.getClose();
if(tempDate.compareTo(maxDay) > 0){
maxDay = tempDate;
}else if(tempDate.compareTo(minDay) < 0){
minDay = tempDate;
}
if(tempClose.get() > max){
max = (int)tempClose.get();
}else if(tempClose.get() < min){
min = (int)tempClose.get();
}
}
String minDayFinal = "" + new SimpleDateFormat("yyyy").format(new Date(minDay.get()));
String maxDayFinal = "" + new SimpleDateFormat("yyyy").format(new Date(maxDay.get()));
String output = minDayFinal + " - " + maxDayFinal + " MIN: " + min + " MAX: " + max;
rText.set(output);
context.write(key, rText);
}
}
我的数据集采用以下格式:
exchange, stock_symbol, date, stock_price_open,stock_price_high,stock_price_low, stock_price_close, stock_volume,stock_price_adj_close.
例如:
NASDAQ,AAPL,1970-10-22, ...
我被要求编写一个新的 MapReduce 程序,为每家公司提供它在股票市场上存在的年限范围,以及股票获得的最大和最小收盘价。
我的程序产生了正确的输出,但由于某种原因开始日期不变:
AAON 1970 - 2002 MIN: 1 MAX: 35
AATI 1970 - 2010 MIN: 2 MAX: 15
ABCO 1970 - 2004 MIN: 14 MAX: 69
ABCW 1970 - 2007 MIN: 0 MAX: 53
ABII 1970 - 2008 MIN: 25 MAX: 78
ABIO 1970 - 1999 MIN: 0 MAX: 139
ABMC 1970 - 2004 MIN: 0 MAX: 6
ABTL 1970 - 2004 MIN: 0 MAX: 58
ACAD 1970 - 2009 MIN: 0 MAX: 17
ACAP 1970 - 2005 MIN: 15 MAX: 55
ACAT 1970 - 2009 MIN: 3 MAX: 29
ACCL 1970 - 1997 MIN: 3 MAX: 104
ACEL 1970 - 1998 MIN: 0 MAX: 10
ACET 1970 - 2004 MIN: 4 MAX: 27
ACFC 1970 - 2008 MIN: 1 MAX: 20
ACGL 1970 - 1997 MIN: 11 MAX: 80
ACLI 1970 - 2006 MIN: 2 MAX: 77
ACLS 1970 - 2001 MIN: 0 MAX: 30
DateClosePair 是客户可写的,我写的就像您在网络上找到的每个示例一样。
很奇怪,min_closing价格和max_closing价格是正确的,而mix_date和max_date价格是错误的。
有什么想法吗?
LongWritable minDay = new LongWritable()
将您的最小日期变量初始化为 1970。
更准确地说:除非给定特定值,否则 LongWritable
会根据 java language spec 将其内部 long
初始化为 0。当它被输入 java.util.Date
时,它被解释为距 Unix 纪元 0 毫秒:January 1, 1970, 00:00:00 UTC
.
我的猜测是 1970 年是数据集中所有日期值的下限。这将为每个键写入它。
我注意到您使用 int min = Integer.MAX_VALUE
来初始化收盘价。也许您可以使用 LongWritable minDay = LongWritable(Long.MAX_VALUE)
来解决?
我已经解决了由别名引起的问题。
我应该调用 .set()
.
方法,而不是 maxDay = tempDate;
现在 maxDay
指向 tempDate
对象
解决方案:
maxDay.set(tempDate.get());
我有以下 Reducer class
public class CompanyMinMaxReducer extends Reducer<Text, DateClosePair, Text, Text> {
private Text rText = new Text();
public void reduce(Text key, Iterable<DateClosePair> values, Context context)
throws IOException, InterruptedException {
int min = Integer.MAX_VALUE;
int max = Integer.MIN_VALUE;
LongWritable minDay = new LongWritable();
LongWritable maxDay = new LongWritable();
for(DateClosePair val: values){
LongWritable tempDate = val.getDate();
DoubleWritable tempClose = val.getClose();
if(tempDate.compareTo(maxDay) > 0){
maxDay = tempDate;
}else if(tempDate.compareTo(minDay) < 0){
minDay = tempDate;
}
if(tempClose.get() > max){
max = (int)tempClose.get();
}else if(tempClose.get() < min){
min = (int)tempClose.get();
}
}
String minDayFinal = "" + new SimpleDateFormat("yyyy").format(new Date(minDay.get()));
String maxDayFinal = "" + new SimpleDateFormat("yyyy").format(new Date(maxDay.get()));
String output = minDayFinal + " - " + maxDayFinal + " MIN: " + min + " MAX: " + max;
rText.set(output);
context.write(key, rText);
}
}
我的数据集采用以下格式:
exchange, stock_symbol, date, stock_price_open,stock_price_high,stock_price_low, stock_price_close, stock_volume,stock_price_adj_close.
例如:
NASDAQ,AAPL,1970-10-22, ...
我被要求编写一个新的 MapReduce 程序,为每家公司提供它在股票市场上存在的年限范围,以及股票获得的最大和最小收盘价。
我的程序产生了正确的输出,但由于某种原因开始日期不变:
AAON 1970 - 2002 MIN: 1 MAX: 35
AATI 1970 - 2010 MIN: 2 MAX: 15
ABCO 1970 - 2004 MIN: 14 MAX: 69
ABCW 1970 - 2007 MIN: 0 MAX: 53
ABII 1970 - 2008 MIN: 25 MAX: 78
ABIO 1970 - 1999 MIN: 0 MAX: 139
ABMC 1970 - 2004 MIN: 0 MAX: 6
ABTL 1970 - 2004 MIN: 0 MAX: 58
ACAD 1970 - 2009 MIN: 0 MAX: 17
ACAP 1970 - 2005 MIN: 15 MAX: 55
ACAT 1970 - 2009 MIN: 3 MAX: 29
ACCL 1970 - 1997 MIN: 3 MAX: 104
ACEL 1970 - 1998 MIN: 0 MAX: 10
ACET 1970 - 2004 MIN: 4 MAX: 27
ACFC 1970 - 2008 MIN: 1 MAX: 20
ACGL 1970 - 1997 MIN: 11 MAX: 80
ACLI 1970 - 2006 MIN: 2 MAX: 77
ACLS 1970 - 2001 MIN: 0 MAX: 30
DateClosePair 是客户可写的,我写的就像您在网络上找到的每个示例一样。
很奇怪,min_closing价格和max_closing价格是正确的,而mix_date和max_date价格是错误的。
有什么想法吗?
LongWritable minDay = new LongWritable()
将您的最小日期变量初始化为 1970。
更准确地说:除非给定特定值,否则 LongWritable
会根据 java language spec 将其内部 long
初始化为 0。当它被输入 java.util.Date
时,它被解释为距 Unix 纪元 0 毫秒:January 1, 1970, 00:00:00 UTC
.
我的猜测是 1970 年是数据集中所有日期值的下限。这将为每个键写入它。
我注意到您使用 int min = Integer.MAX_VALUE
来初始化收盘价。也许您可以使用 LongWritable minDay = LongWritable(Long.MAX_VALUE)
来解决?
我已经解决了由别名引起的问题。
我应该调用 .set()
.
maxDay = tempDate;
现在 maxDay
指向 tempDate
对象
解决方案:
maxDay.set(tempDate.get());