@Override
  public String getName() {
    return FUNCTION_NAME;
  }
@Test
  public void testCastTransformFunction() {
    ExpressionContext expression =
        RequestContextUtils.getExpression(String.format("CAST(%s AS string)", INT_SV_COLUMN));
    TransformFunction transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    assertEquals(transformFunction.getName(), CastTransformFunction.FUNCTION_NAME);
    String[] expectedStringValues = new String[NUM_ROWS];
    String[] scalarStringValues = new String[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedStringValues[i] = Integer.toString(_intSVValues[i]);
      scalarStringValues[i] = (String) cast(_intSVValues[i], "string");
    }
    testTransformFunction(transformFunction, expectedStringValues);
    assertEquals(expectedStringValues, scalarStringValues);

    expression = RequestContextUtils.getExpression(String.format("CAST(CAST(%s as INT) as FLOAT)", FLOAT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    float[] expectedFloatValues = new float[NUM_ROWS];
    float[] scalarFloatValues = new float[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedFloatValues[i] = (int) _floatSVValues[i];
      scalarFloatValues[i] = (float) cast(cast(_floatSVValues[i], "int"), "float");
    }
    testTransformFunction(transformFunction, expectedFloatValues);
    assertEquals(expectedFloatValues, scalarFloatValues);

    expression = RequestContextUtils.getExpression(String.format("CAST(CAST(%s as BOOLEAN) as STRING)", INT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedStringValues[i] = Boolean.toString(_intSVValues[i] != 0);
      scalarStringValues[i] = (String) cast(cast(_intSVValues[i], "boolean"), "string");
    }
    testTransformFunction(transformFunction, expectedStringValues);
    assertEquals(expectedStringValues, scalarStringValues);

    expression =
        RequestContextUtils.getExpression(String.format("CAST(CAST(%s as TIMESTAMP) as STRING)", LONG_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedStringValues[i] = new Timestamp(_longSVValues[i]).toString();
      scalarStringValues[i] = (String) cast(cast(_longSVValues[i], "timestamp"), "string");
    }
    testTransformFunction(transformFunction, expectedStringValues);
    assertEquals(expectedStringValues, scalarStringValues);

    expression = RequestContextUtils.getExpression(String.format("CAST(CAST(%s as BOOLEAN) as INT)", INT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    int[] expectedIntValues = new int[NUM_ROWS];
    int[] scalarIntValues = new int[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedIntValues[i] = _intSVValues[i] != 0 ? 1 : 0;
      scalarIntValues[i] = (int) cast(cast(_intSVValues[i], "boolean"), "int");
    }
    testTransformFunction(transformFunction, expectedIntValues);
    assertEquals(expectedIntValues, scalarIntValues);

    expression = RequestContextUtils.getExpression(
        String.format("CAST(ADD(CAST(%s AS LONG), %s) AS STRING)", DOUBLE_SV_COLUMN, LONG_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedStringValues[i] = Double.toString((double) (long) _doubleSVValues[i] + (double) _longSVValues[i]);
      scalarStringValues[i] =
          (String) cast((double) (long) cast(_doubleSVValues[i], "long") + (double) _longSVValues[i], "string");
    }
    testTransformFunction(transformFunction, expectedStringValues);
    assertEquals(expectedStringValues, scalarStringValues);

    expression = RequestContextUtils.getExpression(
        String.format("caSt(cAst(casT(%s as inT) + %s aS sTring) As DouBle)", FLOAT_SV_COLUMN, INT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    double[] expectedDoubleValues = new double[NUM_ROWS];
    double[] scalarDoubleValues = new double[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedDoubleValues[i] = (double) (int) _floatSVValues[i] + (double) _intSVValues[i];
      scalarDoubleValues[i] =
          (double) cast(cast((double) (int) cast(_floatSVValues[i], "int") + (double) _intSVValues[i], "string"),
              "double");
    }
    testTransformFunction(transformFunction, expectedDoubleValues);
    assertEquals(expectedDoubleValues, scalarDoubleValues);

    expression = RequestContextUtils.getExpression(
        String.format("CAST(CAST(%s AS INT) - CAST(%s AS FLOAT) / CAST(%s AS DOUBLE) AS LONG)", DOUBLE_SV_COLUMN,
            LONG_SV_COLUMN, INT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    long[] expectedLongValues = new long[NUM_ROWS];
    long[] longScalarValues = new long[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedLongValues[i] =
          (long) ((double) (int) _doubleSVValues[i] - (double) (float) _longSVValues[i] / (double) _intSVValues[i]);
      longScalarValues[i] = (long) cast((double) (int) cast(_doubleSVValues[i], "int")
          - (double) (float) cast(_longSVValues[i], "float") / (double) cast(_intSVValues[i], "double"), "long");
    }
    testTransformFunction(transformFunction, expectedLongValues);
    assertEquals(expectedLongValues, longScalarValues);

    expression = RequestContextUtils.getExpression(String.format("CAST(%s AS BIG_DECIMAL)", LONG_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    BigDecimal[] expectedBigDecimalValues = new BigDecimal[NUM_ROWS];
    BigDecimal[] bigDecimalScalarValues = new BigDecimal[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedBigDecimalValues[i] = BigDecimal.valueOf(_longSVValues[i]);
      bigDecimalScalarValues[i] = (BigDecimal) cast(_longSVValues[i], "BIG_DECIMAL");
    }
    testTransformFunction(transformFunction, expectedBigDecimalValues);
    assertEquals(expectedBigDecimalValues, bigDecimalScalarValues);

    expression = RequestContextUtils.getExpression(
        String.format("CAST(CAST(%s AS DOUBLE) - CAST(%s AS DOUBLE) / CAST(%s AS DOUBLE) AS BIG_DECIMAL)",
            BIG_DECIMAL_SV_COLUMN, LONG_SV_COLUMN, INT_SV_COLUMN));
    transformFunction = TransformFunctionFactory.get(expression, _dataSourceMap);
    assertTrue(transformFunction instanceof CastTransformFunction);
    expectedBigDecimalValues = new BigDecimal[NUM_ROWS];
    for (int i = 0; i < NUM_ROWS; i++) {
      expectedBigDecimalValues[i] = BigDecimal.valueOf(
          _bigDecimalSVValues[i].doubleValue() - (double) _longSVValues[i] / (double) _intSVValues[i]);
      double d =
          (double) cast(_bigDecimalSVValues[i], "double") - (double) cast(_longSVValues[i], "double") / (double) cast(
              _intSVValues[i], "double");
      bigDecimalScalarValues[i] = (BigDecimal) cast(d, "BIG_DECIMAL");
    }
    testTransformFunction(transformFunction, expectedBigDecimalValues);
    assertEquals(expectedBigDecimalValues, bigDecimalScalarValues);
  }