diff --git ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java index 6cdaedb..5a13493 100644 --- ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java +++ ql/src/java/org/apache/hadoop/hive/ql/parse/SemanticAnalyzer.java @@ -2328,6 +2328,53 @@ private Operator genFilterPlan(QB qb, ASTNode condn, Operator input) return output; } + /* + * for inner joins push a 'is not null predicate' to the join sources for + * every non nullSafe predicate. + */ + private Operator genNotNullFilterForJoinSourcePlan(QB qb, + int pos, Operator input) throws SemanticException { + + if (!qb.getQbJoinTree().getNoOuterJoin()) { + return input; + } + + ArrayList joiningConds = qb.getQbJoinTree().getExpressions().get(pos); + if (joiningConds == null || joiningConds.size() == 0) { + return input; + } + OpParseContext inputCtx = opParseCtx.get(input); + RowResolver inputRR = inputCtx.getRowResolver(); + + ExprNodeDesc filterPred = null; + for (int i = 0; i < joiningConds.size(); i++) { + ASTNode jC = joiningConds.get(i); + if (qb.getQbJoinTree().getNullSafes().get(i)) { + continue; + } + List args = new ArrayList(); + args.add(genExprNodeDesc(jC, inputRR)); + ExprNodeDesc nextExpr = ExprNodeGenericFuncDesc.newInstance( + FunctionRegistry.getFunctionInfo("isnotnull").getGenericUDF(), args); + filterPred = filterPred == null ? nextExpr : ExprNodeDescUtils + .mergePredicates(filterPred, nextExpr); + } + + if (filterPred == null) { + return input; + } + + Operator output = putOpInsertMap(OperatorFactory.getAndMakeChild( + new FilterDesc(filterPred, false), + new RowSchema(inputRR.getColumnInfos()), input), inputRR); + + if (LOG.isDebugEnabled()) { + LOG.debug("Created Filter Plan for " + qb.getId() + " row schema: " + + inputRR.toString()); + } + return output; + } + @SuppressWarnings("nls") private Integer genColListRegex(String colRegex, String tabAlias, ASTNode sel, ArrayList col_list, @@ -6867,6 +6914,7 @@ private Operator genJoinOperator(QB qb, QBJoinTree joinTree, for (int i = 0; i < srcOps.length; i++) { // generate a ReduceSink operator for the join String[] srcs = baseSrc[i] != null ? new String[] {baseSrc[i]} : joinTree.getLeftAliases(); + srcOps[i] = genNotNullFilterForJoinSourcePlan(qb, i, srcOps[i]); srcOps[i] = genJoinReduceSinkChild(qb, joinKeys[i], srcOps[i], srcs, joinTree.getNextTag()); }