浏览代码

HPCC-2978 Make IF(cond, unicode_x, unicode_y) variable length

Previously an IF() operator with unicode arguments, where both arguments were
fixed length would force the shorter argument to the length of the longer
argument.  E.g.,
  IF (cond, unicode2_field, U'')
was treated as
  IF (cond, unicode2_field, U'  ')

Signed-off-by: Gavin Halliday <gavin.halliday@lexisnexis.com>
Gavin Halliday 10 年之前
父节点
当前提交
640ce78f88
共有 4 个文件被更改,包括 27 次插入2 次删除
  1. 1 1
      ecl/hql/hqlgram2.cpp
  2. 1 1
      ecl/hql/hqlutil.cpp
  3. 21 0
      testing/regress/ecl/issue2978.ecl
  4. 4 0
      testing/regress/ecl/key/issue2978.xml

+ 1 - 1
ecl/hql/hqlgram2.cpp

@@ -3912,7 +3912,7 @@ ITypeInfo *HqlGram::checkPromoteIfType(attribute &a1, attribute &a2)
     ITypeInfo *t2 = a2.queryExprType();
 
     Owned<ITypeInfo> type = ::getPromotedECLType(t1, t2);
-    if (isStringType(type) && (t1->getStringLen() != t2->getStringLen()))
+    if ((isStringType(type) || isUnicodeType(type)) && (t1->getStringLen() != t2->getStringLen()))
         type.setown(getStretchedType(UNKNOWN_LENGTH, type));
 
     ensureType(a1, type);

+ 1 - 1
ecl/hql/hqlutil.cpp

@@ -1492,7 +1492,7 @@ IHqlExpression * createIf(IHqlExpression * cond, IHqlExpression * left, IHqlExpr
     ITypeInfo * leftType = left->queryType();
     ITypeInfo * rightType = right->queryType();
     Owned<ITypeInfo> type = ::getPromotedECLType(leftType, rightType);
-    if (isStringType(type) && (leftType->getStringLen() != rightType->getStringLen()))
+    if ((isStringType(type) || isUnicodeType(type)) && (leftType->getStringLen() != rightType->getStringLen()))
         type.setown(getStretchedType(UNKNOWN_LENGTH, type));
 
     return createValue(no_if, type.getClear(), cond, left, right);

+ 21 - 0
testing/regress/ecl/issue2978.ecl

@@ -0,0 +1,21 @@
+Work1 := RECORD
+  UNSIGNED4 key;
+  UNSIGNED4 pos;
+  UNSIGNED4 len;
+  UNICODE tok;
+END;
+
+ds := DATASET([{1,  1, 3,  u'abc'}
+              ,{1,  4, 1,  u','}
+              ,{1,  6, 1,  u'Z'}
+              ,{2,  1, 3,  u'abc'}
+              ,{2,  5, 3,  u'def'}], Work1);
+
+ Work1 roll1(Work1 cumm, Work1 curr) := TRANSFORM
+  SELF.tok := cumm.tok + IF(cumm.pos + cumm.len < curr.pos, u' ', u'') + curr.tok;
+  SELF.len := cumm.len + IF(cumm.pos + cumm.len < curr.pos, 1, 0) + curr.len;
+  SELF := cumm;
+ END;
+
+d1 := ROLLUP(ds, roll1(LEFT,RIGHT), key, LOCAL);
+OUTPUT(d1);

+ 4 - 0
testing/regress/ecl/key/issue2978.xml

@@ -0,0 +1,4 @@
+<Dataset name='Result 1'>
+ <Row><key>1</key><pos>1</pos><len>6</len><tok>abc, Z</tok></Row>
+ <Row><key>2</key><pos>1</pos><len>7</len><tok>abc def</tok></Row>
+</Dataset>