@@ -26,10 +26,22 @@ object HiveTypeCoercion {
2626 // See https://cwiki.apache.org/confluence/display/Hive/LanguageManual+Types.
2727 // The conversion for integral and floating point types have a linear widening hierarchy:
2828 val numericPrecedence =
29- Seq (NullType , ByteType , ShortType , IntegerType , LongType , FloatType , DoubleType , DecimalType )
30- // Boolean is only wider than Void
31- val booleanPrecedence = Seq (NullType , BooleanType )
32- val allPromotions : Seq [Seq [DataType ]] = numericPrecedence :: booleanPrecedence :: Nil
29+ Seq (ByteType , ShortType , IntegerType , LongType , FloatType , DoubleType , DecimalType )
30+ val allPromotions : Seq [Seq [DataType ]] = numericPrecedence :: Nil
31+
32+ def findTightestCommonType (t1 : DataType , t2 : DataType ): Option [DataType ] = {
33+ val valueTypes = Seq (t1, t2).filter(t => t != NullType )
34+ if (valueTypes.distinct.size > 1 ) {
35+ // Try and find a promotion rule that contains both types in question.
36+ val applicableConversion =
37+ HiveTypeCoercion .allPromotions.find(p => p.contains(t1) && p.contains(t2))
38+
39+ // If found return the widest common type, otherwise None
40+ applicableConversion.map(_.filter(t => t == t1 || t == t2).last)
41+ } else {
42+ Some (if (valueTypes.size == 0 ) NullType else valueTypes.head)
43+ }
44+ }
3345}
3446
3547/**
@@ -53,17 +65,6 @@ trait HiveTypeCoercion {
5365 Division ::
5466 Nil
5567
56- trait TypeWidening {
57- def findTightestCommonType (t1 : DataType , t2 : DataType ): Option [DataType ] = {
58- // Try and find a promotion rule that contains both types in question.
59- val applicableConversion =
60- HiveTypeCoercion .allPromotions.find(p => p.contains(t1) && p.contains(t2))
61-
62- // If found return the widest common type, otherwise None
63- applicableConversion.map(_.filter(t => t == t1 || t == t2).last)
64- }
65- }
66-
6768 /**
6869 * Applies any changes to [[AttributeReference ]] data types that are made by other rules to
6970 * instances higher in the query tree.
@@ -144,7 +145,8 @@ trait HiveTypeCoercion {
144145 * - LongType to FloatType
145146 * - LongType to DoubleType
146147 */
147- object WidenTypes extends Rule [LogicalPlan ] with TypeWidening {
148+ object WidenTypes extends Rule [LogicalPlan ] {
149+ import HiveTypeCoercion ._
148150
149151 def apply (plan : LogicalPlan ): LogicalPlan = plan transform {
150152 case u @ Union (left, right) if u.childrenResolved && ! u.resolved =>
@@ -352,7 +354,9 @@ trait HiveTypeCoercion {
352354 /**
353355 * Coerces the type of different branches of a CASE WHEN statement to a common type.
354356 */
355- object CaseWhenCoercion extends Rule [LogicalPlan ] with TypeWidening {
357+ object CaseWhenCoercion extends Rule [LogicalPlan ] {
358+ import HiveTypeCoercion ._
359+
356360 def apply (plan : LogicalPlan ): LogicalPlan = plan transformAllExpressions {
357361 case cw @ CaseWhen (branches) if ! cw.resolved && ! branches.exists(! _.resolved) =>
358362 val valueTypes = branches.sliding(2 , 2 ).map {
0 commit comments