Skip to content

Commit

Permalink
GROOVY-8488: STC: float or double can accept a BigDecimal literal
Browse files Browse the repository at this point in the history
3_0_X backport
  • Loading branch information
eric-milles committed Nov 3, 2023
1 parent d56990f commit 542e1e5
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -175,8 +175,8 @@ public abstract class StaticTypeCheckingSupport {
Short_TYPE, 1,
int_TYPE, 2,
Integer_TYPE, 2,
Long_TYPE, 3,
long_TYPE, 3,
Long_TYPE, 3,
float_TYPE, 4,
Float_TYPE, 4,
double_TYPE, 5,
Expand Down Expand Up @@ -453,8 +453,11 @@ public static boolean isAssignableTo(ClassNode type, ClassNode toBeAssignedTo) {
if (type == toBeAssignedTo || type == UNKNOWN_PARAMETER_TYPE) return true;
if (isPrimitiveType(type)) type = getWrapper(type);
if (isPrimitiveType(toBeAssignedTo)) toBeAssignedTo = getWrapper(toBeAssignedTo);
if (NUMBER_TYPES.containsKey(type.redirect()) && NUMBER_TYPES.containsKey(toBeAssignedTo.redirect())) {
return NUMBER_TYPES.get(type.redirect()) <= NUMBER_TYPES.get(toBeAssignedTo.redirect());
Integer source= NUMBER_TYPES.get(type), target= NUMBER_TYPES.get(toBeAssignedTo);
if (source != null && target != null) { return (source.compareTo(target) <= 0); }
// GROOVY-8325, GROOVY-8488: float or double can be assigned a BigDecimal literal
if (BigDecimal_TYPE.equals(type) && (Double_TYPE.equals(toBeAssignedTo) || Float_TYPE.equals(toBeAssignedTo))) {
return true;
}
if (type.isArray() && toBeAssignedTo.isArray()) {
ClassNode sourceComponent = type.getComponentType(), targetComponent = toBeAssignedTo.getComponentType();
Expand Down
36 changes: 36 additions & 0 deletions src/test/groovy/transform/stc/MethodCallsSTCTest.groovy
Original file line number Diff line number Diff line change
Expand Up @@ -944,6 +944,42 @@ class MethodCallsSTCTest extends StaticTypeCheckingTestCase {
}
}

// GROOVY-8488
void testBigDecimalLiteralArgument() {
assertScript '''
def m1(double d) { Double.valueOf(d) }
def m2(float f) { Float.valueOf(f) }
assert m1(1.0) == 1.0d
assert m2(1.0) == 1.0f
'''

shouldFailWithMessages '''
class C {
def m1(long l) { Long.valueOf(l) }
def m2(int i) { new Integer(i) }
void test() {
m1(1.0)
m2(1.0)
}
}
''',
'Cannot find matching method C#m1(java.math.BigDecimal)',
'Cannot find matching method C#m2(java.math.BigDecimal)'

shouldFailWithMessages '''
class C {
def m1(long l) { Long.valueOf(l) }
def m2(int i) { new Integer(i) }
void test() {
m1(1g)
m2(1g)
}
}
''',
'Cannot find matching method C#m1(java.math.BigInteger)',
'Cannot find matching method C#m2(java.math.BigInteger)'
}

void testBoxingShouldCostMore() {
assertScript '''
int foo(int x) { 1 }
Expand Down

0 comments on commit 542e1e5

Please sign in to comment.