casts supported
This commit is contained in:
@@ -28,7 +28,7 @@ public class JetBinaryExpressionWithTypeRHS extends JetExpression {
|
|||||||
|
|
||||||
@Nullable @IfNotParsed
|
@Nullable @IfNotParsed
|
||||||
public JetTypeReference getRight() {
|
public JetTypeReference getRight() {
|
||||||
ASTNode node = getOperationReference().getNode();
|
ASTNode node = getOperationSign().getNode();
|
||||||
while (node != null) {
|
while (node != null) {
|
||||||
PsiElement psi = node.getPsi();
|
PsiElement psi = node.getPsi();
|
||||||
if (psi instanceof JetTypeReference) {
|
if (psi instanceof JetTypeReference) {
|
||||||
@@ -40,7 +40,7 @@ public class JetBinaryExpressionWithTypeRHS extends JetExpression {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@NotNull
|
@NotNull
|
||||||
public JetSimpleNameExpression getOperationReference() {
|
public JetSimpleNameExpression getOperationSign() {
|
||||||
return (JetSimpleNameExpression) findChildByType(JetNodeTypes.OPERATION_REFERENCE);
|
return (JetSimpleNameExpression) findChildByType(JetNodeTypes.OPERATION_REFERENCE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -16,6 +16,46 @@ import java.util.*;
|
|||||||
*/
|
*/
|
||||||
public class JetTypeInferrer {
|
public class JetTypeInferrer {
|
||||||
|
|
||||||
|
private static final Map<IElementType, String> unaryOperationNames = new HashMap<IElementType, String>();
|
||||||
|
static {
|
||||||
|
unaryOperationNames.put(JetTokens.PLUSPLUS, "inc");
|
||||||
|
unaryOperationNames.put(JetTokens.MINUSMINUS, "dec");
|
||||||
|
unaryOperationNames.put(JetTokens.EXCL, "not");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final Map<IElementType, String> binaryOperationNames = new HashMap<IElementType, String>();
|
||||||
|
static {
|
||||||
|
binaryOperationNames.put(JetTokens.MUL, "times");
|
||||||
|
binaryOperationNames.put(JetTokens.PLUS, "plus");
|
||||||
|
binaryOperationNames.put(JetTokens.MINUS, "minus");
|
||||||
|
binaryOperationNames.put(JetTokens.DIV, "div");
|
||||||
|
binaryOperationNames.put(JetTokens.PERC, "mod");
|
||||||
|
binaryOperationNames.put(JetTokens.ARROW, "arrow");
|
||||||
|
binaryOperationNames.put(JetTokens.RANGE, "rangeTo");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final Set<IElementType> comparisonOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.LT, JetTokens.GT, JetTokens.LTEQ, JetTokens.GTEQ));
|
||||||
|
private static final Set<IElementType> equalsOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.EQEQ, JetTokens.EXCLEQ));
|
||||||
|
private static final Set<IElementType> inOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.IN_KEYWORD, JetTokens.NOT_IN));
|
||||||
|
|
||||||
|
private static final Map<IElementType, String> assignmentOperationNames = new HashMap<IElementType, String>();
|
||||||
|
static {
|
||||||
|
assignmentOperationNames.put(JetTokens.MULTEQ, "timesAssign");
|
||||||
|
assignmentOperationNames.put(JetTokens.DIVEQ, "divAssign");
|
||||||
|
assignmentOperationNames.put(JetTokens.PERCEQ, "modAssign");
|
||||||
|
assignmentOperationNames.put(JetTokens.PLUSEQ, "plusAssign");
|
||||||
|
assignmentOperationNames.put(JetTokens.MINUSEQ, "minusAssign");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final Map<IElementType, IElementType> assignmentOperationCounterparts = new HashMap<IElementType, IElementType>();
|
||||||
|
static {
|
||||||
|
assignmentOperationCounterparts.put(JetTokens.MULTEQ, JetTokens.MUL);
|
||||||
|
assignmentOperationCounterparts.put(JetTokens.DIVEQ, JetTokens.DIV);
|
||||||
|
assignmentOperationCounterparts.put(JetTokens.PERCEQ, JetTokens.PERC);
|
||||||
|
assignmentOperationCounterparts.put(JetTokens.PLUSEQ, JetTokens.PLUS);
|
||||||
|
assignmentOperationCounterparts.put(JetTokens.MINUSEQ, JetTokens.MINUS);
|
||||||
|
}
|
||||||
|
|
||||||
private final BindingTrace trace;
|
private final BindingTrace trace;
|
||||||
private final JetSemanticServices semanticServices;
|
private final JetSemanticServices semanticServices;
|
||||||
private final TypeResolver typeResolver;
|
private final TypeResolver typeResolver;
|
||||||
@@ -354,17 +394,24 @@ public class JetTypeInferrer {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void visitBinaryWithTypeRHSExpression(JetBinaryExpressionWithTypeRHS expression) {
|
public void visitBinaryWithTypeRHSExpression(JetBinaryExpressionWithTypeRHS expression) {
|
||||||
if (expression.getOperationReference().getReferencedNameElementType() == JetTokens.COLON) {
|
IElementType operationType = expression.getOperationSign().getReferencedNameElementType();
|
||||||
JetType actualType = getType(scope, expression.getLeft(), false);
|
JetType actualType = getType(scope, expression.getLeft(), false);
|
||||||
JetType expectedType = typeResolver.resolveType(scope, expression.getRight());
|
JetTypeReference right = expression.getRight();
|
||||||
if (actualType != null && !semanticServices.getTypeChecker().isSubtypeOf(actualType, expectedType)) {
|
if (right != null) {
|
||||||
// TODO
|
JetType targetType = typeResolver.resolveType(scope, right);
|
||||||
semanticServices.getErrorHandler().typeMismatch(expression.getLeft(), expectedType, actualType);
|
if (operationType == JetTokens.COLON) {
|
||||||
|
if (actualType != null && !semanticServices.getTypeChecker().isSubtypeOf(actualType, targetType)) {
|
||||||
|
semanticServices.getErrorHandler().typeMismatch(expression.getLeft(), targetType, actualType);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
result = expectedType;
|
else if (operationType == JetTokens.AS_KEYWORD) {
|
||||||
return;
|
// TODO : Check for cast impossibility
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
semanticServices.getErrorHandler().structuralError(expression.getOperationSign().getNode(), "Unsupported binary operation");
|
||||||
|
}
|
||||||
|
result = targetType;
|
||||||
}
|
}
|
||||||
throw new UnsupportedOperationException(); // TODO
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -698,46 +745,4 @@ public class JetTypeInferrer {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final Map<IElementType, String> unaryOperationNames = new HashMap<IElementType, String>();
|
|
||||||
static {
|
|
||||||
unaryOperationNames.put(JetTokens.PLUSPLUS, "inc");
|
|
||||||
unaryOperationNames.put(JetTokens.MINUSMINUS, "dec");
|
|
||||||
unaryOperationNames.put(JetTokens.EXCL, "not");
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final Map<IElementType, String> binaryOperationNames = new HashMap<IElementType, String>();
|
|
||||||
static {
|
|
||||||
binaryOperationNames.put(JetTokens.MUL, "times");
|
|
||||||
binaryOperationNames.put(JetTokens.PLUS, "plus");
|
|
||||||
binaryOperationNames.put(JetTokens.MINUS, "minus");
|
|
||||||
binaryOperationNames.put(JetTokens.DIV, "div");
|
|
||||||
binaryOperationNames.put(JetTokens.PERC, "mod");
|
|
||||||
binaryOperationNames.put(JetTokens.ARROW, "arrow");
|
|
||||||
binaryOperationNames.put(JetTokens.RANGE, "rangeTo");
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final Set<IElementType> comparisonOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.LT, JetTokens.GT, JetTokens.LTEQ, JetTokens.GTEQ));
|
|
||||||
private static final Set<IElementType> equalsOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.EQEQ, JetTokens.EXCLEQ));
|
|
||||||
private static final Set<IElementType> inOperations = new HashSet<IElementType>(Arrays.asList(JetTokens.IN_KEYWORD, JetTokens.NOT_IN));
|
|
||||||
|
|
||||||
private static final Map<IElementType, String> assignmentOperationNames = new HashMap<IElementType, String>();
|
|
||||||
static {
|
|
||||||
assignmentOperationNames.put(JetTokens.MULTEQ, "timesAssign");
|
|
||||||
assignmentOperationNames.put(JetTokens.DIVEQ, "divAssign");
|
|
||||||
assignmentOperationNames.put(JetTokens.PERCEQ, "modAssign");
|
|
||||||
assignmentOperationNames.put(JetTokens.PLUSEQ, "plusAssign");
|
|
||||||
assignmentOperationNames.put(JetTokens.MINUSEQ, "minusAssign");
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final Map<IElementType, IElementType> assignmentOperationCounterparts = new HashMap<IElementType, IElementType>();
|
|
||||||
static {
|
|
||||||
assignmentOperationCounterparts.put(JetTokens.MULTEQ, JetTokens.MUL);
|
|
||||||
assignmentOperationCounterparts.put(JetTokens.DIVEQ, JetTokens.DIV);
|
|
||||||
assignmentOperationCounterparts.put(JetTokens.PERCEQ, JetTokens.PERC);
|
|
||||||
assignmentOperationCounterparts.put(JetTokens.PLUSEQ, JetTokens.PLUS);
|
|
||||||
assignmentOperationCounterparts.put(JetTokens.MINUSEQ, JetTokens.MINUS);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -398,6 +398,10 @@ public class JetTypeCheckerTest extends LightDaemonAnalyzerTestCase {
|
|||||||
assertType("\"1\".plus('1')", "String");
|
assertType("\"1\".plus('1')", "String");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testBinaryOperations() throws Exception {
|
||||||
|
assertType("1 as Any", "Any");
|
||||||
|
}
|
||||||
|
|
||||||
private void assertSubtype(String type1, String type2) {
|
private void assertSubtype(String type1, String type2) {
|
||||||
assertSubtypingRelation(type1, type2, true);
|
assertSubtypingRelation(type1, type2, true);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user