Search in sources :

Example 21 with GenericsType

use of org.codehaus.groovy.ast.GenericsType in project groovy by apache.

the class StaticTypeCheckingVisitor method makeOwnerList.

/**
     * Given an object expression (a receiver expression), generate the list of potential receiver types.
     * @param objectExpression the receiver expression
     * @return the list of types the receiver may be
     */
protected List<Receiver<String>> makeOwnerList(final Expression objectExpression) {
    final ClassNode receiver = getType(objectExpression);
    List<Receiver<String>> owners = new LinkedList<Receiver<String>>();
    owners.add(Receiver.<String>make(receiver));
    if (isClassClassNodeWrappingConcreteType(receiver)) {
        GenericsType clazzGT = receiver.getGenericsTypes()[0];
        owners.add(0, Receiver.<String>make(clazzGT.getType()));
    }
    if (receiver.isInterface()) {
        // GROOVY-xxxx
        owners.add(Receiver.<String>make(OBJECT_TYPE));
    }
    addSelfTypes(receiver, owners);
    if (!typeCheckingContext.temporaryIfBranchTypeInformation.empty()) {
        List<ClassNode> potentialReceiverType = getTemporaryTypesForExpression(objectExpression);
        if (potentialReceiverType != null) {
            for (ClassNode node : potentialReceiverType) {
                owners.add(Receiver.<String>make(node));
            }
        }
    }
    if (typeCheckingContext.lastImplicitItType != null && objectExpression instanceof VariableExpression && ((VariableExpression) objectExpression).getName().equals("it")) {
        owners.add(Receiver.<String>make(typeCheckingContext.lastImplicitItType));
    }
    return owners;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) GenericsType(org.codehaus.groovy.ast.GenericsType) LinkedList(java.util.LinkedList)

Example 22 with GenericsType

use of org.codehaus.groovy.ast.GenericsType in project groovy by apache.

the class StaticTypeCheckingVisitor method adjustTypeForSpreading.

private static ClassNode adjustTypeForSpreading(ClassNode inferredRightExpressionType, Expression leftExpression) {
    // imagine we have: list*.foo = 100
    // then the assignment must be checked against [100], not 100
    ClassNode wrappedRHS = inferredRightExpressionType;
    if (leftExpression instanceof PropertyExpression && ((PropertyExpression) leftExpression).isSpreadSafe()) {
        wrappedRHS = LIST_TYPE.getPlainNodeReference();
        wrappedRHS.setGenericsTypes(new GenericsType[] { new GenericsType(getWrapper(inferredRightExpressionType)) });
    }
    return wrappedRHS;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) GenericsType(org.codehaus.groovy.ast.GenericsType)

Example 23 with GenericsType

use of org.codehaus.groovy.ast.GenericsType in project groovy by apache.

the class StaticTypeCheckingVisitor method inferListExpressionType.

protected ClassNode inferListExpressionType(final ListExpression list) {
    List<Expression> expressions = list.getExpressions();
    if (expressions.isEmpty()) {
        // cannot infer, return list type
        return list.getType();
    }
    ClassNode listType = list.getType();
    GenericsType[] genericsTypes = listType.getGenericsTypes();
    if ((genericsTypes == null || genericsTypes.length == 0 || (genericsTypes.length == 1 && OBJECT_TYPE.equals(genericsTypes[0].getType()))) && (!expressions.isEmpty())) {
        // maybe we can infer the component type
        List<ClassNode> nodes = new LinkedList<ClassNode>();
        for (Expression expression : expressions) {
            if (isNullConstant(expression)) {
            // a null element is found in the list, skip it because we'll use the other elements from the list
            } else {
                nodes.add(getType(expression));
            }
        }
        if (nodes.isEmpty()) {
            // every element was the null constant
            return listType;
        }
        // to be used in generics, type must be boxed
        ClassNode superType = getWrapper(lowestUpperBound(nodes));
        ClassNode inferred = listType.getPlainNodeReference();
        inferred.setGenericsTypes(new GenericsType[] { new GenericsType(wrapTypeIfNecessary(superType)) });
        return inferred;
    }
    return listType;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) GenericsType(org.codehaus.groovy.ast.GenericsType) LinkedList(java.util.LinkedList)

Example 24 with GenericsType

use of org.codehaus.groovy.ast.GenericsType in project groovy by apache.

the class StaticTypeCheckingVisitor method wrapClosureType.

private static ClassNode wrapClosureType(final ClassNode returnType) {
    ClassNode inferredType = CLOSURE_TYPE.getPlainNodeReference();
    inferredType.setGenericsTypes(new GenericsType[] { new GenericsType(wrapTypeIfNecessary(returnType)) });
    return inferredType;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) GenericsType(org.codehaus.groovy.ast.GenericsType)

Example 25 with GenericsType

use of org.codehaus.groovy.ast.GenericsType in project groovy by apache.

the class StaticTypeCheckingVisitor method inferLoopElementType.

/**
     * Given a loop collection type, returns the inferred type of the loop element. Used, for
     * example, to infer the element type of a (for e in list) loop.
     *
     * @param collectionType the type of the collection
     * @return the inferred component type
     */
public static ClassNode inferLoopElementType(final ClassNode collectionType) {
    ClassNode componentType = collectionType.getComponentType();
    if (componentType == null) {
        if (implementsInterfaceOrIsSubclassOf(collectionType, ITERABLE_TYPE)) {
            ClassNode intf = GenericsUtils.parameterizeType(collectionType, ITERABLE_TYPE);
            GenericsType[] genericsTypes = intf.getGenericsTypes();
            componentType = genericsTypes[0].getType();
        } else if (implementsInterfaceOrIsSubclassOf(collectionType, MAP_TYPE)) {
            // GROOVY-6240
            ClassNode intf = GenericsUtils.parameterizeType(collectionType, MAP_TYPE);
            GenericsType[] genericsTypes = intf.getGenericsTypes();
            componentType = MAP_ENTRY_TYPE.getPlainNodeReference();
            componentType.setGenericsTypes(genericsTypes);
        } else if (STRING_TYPE.equals(collectionType)) {
            componentType = ClassHelper.Character_TYPE;
        } else if (ENUMERATION_TYPE.equals(collectionType)) {
            // GROOVY-6123
            ClassNode intf = GenericsUtils.parameterizeType(collectionType, ENUMERATION_TYPE);
            GenericsType[] genericsTypes = intf.getGenericsTypes();
            componentType = genericsTypes[0].getType();
        } else {
            componentType = ClassHelper.OBJECT_TYPE;
        }
    }
    return componentType;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) GenericsType(org.codehaus.groovy.ast.GenericsType)

Aggregations

GenericsType (org.codehaus.groovy.ast.GenericsType)165 ClassNode (org.codehaus.groovy.ast.ClassNode)143 InnerClassNode (org.codehaus.groovy.ast.InnerClassNode)71 LowestUpperBoundClassNode (org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode)52 Parameter (org.codehaus.groovy.ast.Parameter)20 ClosureSignatureHint (groovy.transform.stc.ClosureSignatureHint)19 MethodNode (org.codehaus.groovy.ast.MethodNode)19 LinkedList (java.util.LinkedList)18 HashMap (java.util.HashMap)17 ArrayList (java.util.ArrayList)15 LinkedHashMap (java.util.LinkedHashMap)9 AST (antlr.collections.AST)8 AnnotationNode (org.codehaus.groovy.ast.AnnotationNode)8 ListHashMap (org.codehaus.groovy.util.ListHashMap)8 Map (java.util.Map)6 AtomicReference (java.util.concurrent.atomic.AtomicReference)6 EnumConstantClassNode (org.codehaus.groovy.ast.EnumConstantClassNode)6 FieldNode (org.codehaus.groovy.ast.FieldNode)6 GroovyBugError (org.codehaus.groovy.GroovyBugError)5 DynamicVariable (org.codehaus.groovy.ast.DynamicVariable)4