@Override
	protected boolean doSecondPhase(String query, Configuration conf, String outputPath, String[] table,
			String[] filter_table, int numberOfReducer) {
		try {
			List<String> dimension_talbe = new ArrayList<String>();
			dimension_talbe.add(TABLE_CUSTOMER);
			dimension_talbe.add(TABLE_DATE);
			dimension_talbe.add(TABLE_PART);
			dimension_talbe.add(TABLE_SUPPLIER);

			DistributedCache.addCacheFile(new URI(FULL_PATH_COLUMN), conf);
			DistributedCache.addCacheFile(new URI(FULL_PATH_JOIN), conf);

			for (String t : filter_table) {
				DistributedCache.addCacheFile(new URI(PATH_BLOOM_FILTER + SYSTEM_SPLIT + dimension_talbe.indexOf(t)),
						conf);
			}
			conf.setLong(MAPRED_TASK_TIMEOUT, Long.MAX_VALUE);
			Job job = new Job(conf, FUNCTION_NAME + " Second Phase " + query);
			job.setJarByClass(TJSGM.class);
			job.setMapperClass(SecondPhaseMapper.class);
			job.setPartitionerClass(TJSGMKeyPartitioner.class);
			job.setNumReduceTasks(numberOfReducer);
			job.setReducerClass(SecondPhaseReducer.class);
			job.setOutputKeyClass(QuadTextPair.class);
			job.setOutputValueClass(Text.class);
			FileInputFormat.addInputPath(job, new Path(PATH_INPUT + SYSTEM_SPLIT + TABLE_LINEORDER + SYSTEM_SPLIT));// fact
			FileInputFormat.addInputPath(job, new Path(PATH_OUTPUT_FIRST));// 第一階段結果
			List<String> list = new ArrayList<String>();
			for (String s : table) {// all need table
				if (!s.equals(TABLE_LINEORDER)) {
					list.add(s);
				}
			}
			for (String s : filter_table) {// filtered table
				list.remove(s);
			}
			for (String t : list) {// non-filter table
				FileInputFormat.addInputPath(job, new Path(PATH_INPUT + SYSTEM_SPLIT + t + SYSTEM_SPLIT));
			}
			CheckAndDelete.checkAndDelete(outputPath, conf);
			FileOutputFormat.setOutputPath(job, new Path(outputPath));

			return job.waitForCompletion(true);
		} catch (URISyntaxException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (InterruptedException e) {
			e.printStackTrace();
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		}
		return false;
	}