@Override public WildcardTypeReference newWildcardTypeReference() { return new WildcardTypeReference(this); }
@Override protected LightweightTypeReference doVisitWildcardTypeReference(WildcardTypeReference reference, ConstraintVisitingInfo visiting) { if (reference.isResolved() && reference.isOwnedBy(getOwner())) return reference; LightweightTypeReference lowerBound = reference.getLowerBound(); if (lowerBound instanceof UnboundTypeReference) { if (!handles.add(((UnboundTypeReference) lowerBound).getHandle())) { WildcardTypeReference result = getOwner().newWildcardTypeReference(); for(LightweightTypeReference upperBound: reference.getUpperBounds()) { result.addUpperBound(visitTypeArgument(upperBound, visiting)); } return result; } } return super.doVisitWildcardTypeReference(reference, visiting); }
@Override protected List<LightweightTypeReference> getSuperTypes(TypeParameterSubstitutor<?> substitutor) { if (isUnbounded()) { return Collections.singletonList(getUpperBoundSubstitute()); } List<LightweightTypeReference> nonNullUpperBounds = expose(getUpperBounds()); List<LightweightTypeReference> result = Lists.newArrayListWithCapacity(nonNullUpperBounds.size()); for(LightweightTypeReference upperBound: nonNullUpperBounds) { result.add(substitutor.substitute(upperBound)); } return result; }
@Override protected LightweightTypeReference doVisitWildcardTypeReference(WildcardTypeReference reference, ResourceSet resourceSet) { if (reference.isUnbounded()) { return reference.getUpperBoundSubstitute(); } if (reference.getUpperBounds().size() == 1) { return reference.getUpperBoundSubstitute().accept(this, resourceSet); } CompoundTypeReference result = reference.getOwner().newCompoundTypeReference(false); enhanceCompoundReference(reference.getUpperBounds(), result, resourceSet); return result; }
@Override /* @Nullable */ public LightweightTypeReference getSuperType(Class<?> rawType) { if (isUnbounded()) { if (Object.class.equals(rawType)) { return internalFindTopLevelType(rawType); } return null; } List<LightweightTypeReference> nonNullUpperBounds = expose(getUpperBounds()); for(LightweightTypeReference upperBound: nonNullUpperBounds) { LightweightTypeReference result = upperBound.getSuperType(rawType); if (result != null) return result; } return null; }
@Override protected void doVisitWildcardTypeReference(WildcardTypeReference reference, ArrayTypeReference declaration) { LightweightTypeReference lowerBound = reference.getLowerBound(); if (lowerBound != null) { outerVisit(declaration, lowerBound, declaration, expectedVariance, VarianceInfo.IN); } else { for(LightweightTypeReference upperBound: reference.getUpperBounds()) { outerVisit(declaration, upperBound, declaration, expectedVariance, VarianceInfo.OUT); } } } }
@Override protected LocalTypeSubstitutor.SubstitutionResult doVisitWildcardTypeReference(WildcardTypeReference reference, VarianceInfo varianceInfo) { WildcardTypeReference result = owner.newWildcardTypeReference(); LightweightTypeReference lowerBound = reference.getLowerBound(); boolean didSubstitute = false; if (lowerBound != null) { SubstitutionResult visited = lowerBound.accept(this, VarianceInfo.IN); result.setLowerBound(visited.typeReference); didSubstitute = didSubstitute || visited.didSubstitute; } for(LightweightTypeReference upperBound: reference.getUpperBounds()) { SubstitutionResult visited = upperBound.accept(this, VarianceInfo.OUT); result.addUpperBound(visited.typeReference); didSubstitute = didSubstitute || visited.didSubstitute; } if (result.getUpperBounds().isEmpty()) { throw new IllegalStateException("UpperBounds may not be empty"); } return new SubstitutionResult(result, didSubstitute); }
@Override /* @Nullable */ public LightweightTypeReference getSuperType(JvmType rawType) { if (isUnbounded()) { if (Object.class.getName().equals(rawType.getIdentifier())) { return getOwner().newParameterizedTypeReference(rawType); } return null; } List<LightweightTypeReference> nonNullUpperBounds = expose(getUpperBounds()); for(LightweightTypeReference upperBound: nonNullUpperBounds) { LightweightTypeReference result = upperBound.getSuperType(rawType); if (result != null) return result; } return null; }
if (i == typeParameters.size() - 1 && parameterReference.equals(functionType.getReturnType())) { WildcardTypeReference wildcard = owner.newWildcardTypeReference(); wildcard.addUpperBound(parameterReference); parameterReferences.add(wildcard); } else if (functionType.getParameterTypes().contains(parameterReference)) { WildcardTypeReference wildcard = owner.newWildcardExtendsObject(); wildcard.setLowerBound(parameterReference); parameterReferences.add(wildcard); } else {
@Override protected Boolean doVisitWildcardTypeReference(WildcardTypeReference reference) { if (reference.isResolved()) { return true; } if (!visit(reference.getUpperBounds())) { return false; } LightweightTypeReference lowerBound = reference.getLowerBound(); if (lowerBound != null) { return lowerBound.accept(this); } return true; }
@Override public LightweightTypeReference getUpperBoundSubstitute() { if (isUnbounded()) { return getOwner().newReferenceToObject(); } List<LightweightTypeReference> upperBounds = getUpperBounds(); if (upperBounds.size() == 1) { LightweightTypeReference result = upperBounds.get(0); return result; } CompoundTypeReference result = getOwner().newCompoundTypeReference(false); for(LightweightTypeReference upperBound: upperBounds) { result.addComponent(upperBound); } return result; }
/** * Creates a new wildcard type reference with the given type as the lower bound and {@link Object} as upper bound. * * For example: * <pre>wildcardSuper(typeRef(CharSequence))</pre> * would create a type reference representing * <pre>? super CharSequence</pre> * * @param superBound * the super bound of the wildcard * @return the newly created wildcard type reference */ public JvmTypeReference wildcardSuper(JvmTypeReference superBound) { WildcardTypeReference wildcardTypeReference = typeReferenceOwner.newWildcardTypeReference(); wildcardTypeReference.addUpperBound(typeReferenceOwner.toLightweightTypeReference(typeRef(Object.class))); wildcardTypeReference.setLowerBound(typeReferenceOwner.toLightweightTypeReference(superBound)); return wildcardTypeReference.toTypeReference(); }
@Override public JvmTypeReference toJavaCompliantTypeReference(IVisibilityHelper helper) { TypesFactory typesFactory = getTypesFactory(); JvmWildcardTypeReference result = typesFactory.createJvmWildcardTypeReference(); if (upperBounds != null && !upperBounds.isEmpty()) { List<LightweightTypeReference> nonInterfaceTypes = getNonInterfaceTypes(upperBounds); JvmTypeReference upperBound = toJavaCompliantTypeReference(nonInterfaceTypes != null ? nonInterfaceTypes: upperBounds, helper); JvmUpperBound constraint = typesFactory.createJvmUpperBound(); constraint.setTypeReference(upperBound); result.getConstraints().add(constraint); } if (lowerBound != null) { JvmLowerBound constraint = typesFactory.createJvmLowerBound(); constraint.setTypeReference(lowerBound.toJavaCompliantTypeReference()); result.getConstraints().add(constraint); } return result; }
/** * Creates a wildcard reference to {@link Object} or returns a wildcard to an {@link UnknownTypeReference} if no * JRE is available. */ @Override public WildcardTypeReference newWildcardExtendsObject() { WildcardTypeReference result = newWildcardTypeReference(); result.addUpperBound(newReferenceToObject()); return result; }
@Override protected List<JvmType> doVisitWildcardTypeReference(WildcardTypeReference reference, ResourceSet resourceSet) { if (reference.isUnbounded()) { return createObjectReference(resourceSet); } List<LightweightTypeReference> upperBounds = reference.getUpperBounds(); if (upperBounds.isEmpty()) { throw new IllegalStateException("UpperBounds may not be empty"); } return collectRawTypes(upperBounds, resourceSet); }
/** * Creates a new wildcard type reference with the given type as the upper bound. * For example: * <pre>wildcardExtends(typeRef(CharSequence))</pre> * would create a type reference representing * <pre>? extends CharSequence</pre> * * @param extendsBound * the upper bound of the wildcard * @return the newly created wildcard type reference */ public JvmTypeReference wildcardExtends(JvmTypeReference extendsBound) { WildcardTypeReference wildcardTypeReference = typeReferenceOwner.newWildcardTypeReference(); wildcardTypeReference.addUpperBound(typeReferenceOwner.toLightweightTypeReference(extendsBound)); return wildcardTypeReference.toTypeReference(); }
/** * The map type may be constructed from different pairs, e.g. the pair's type arguments don't need to be as strict * as the map suggests. The pair's expectation is adjusted accordingly. */ protected LightweightTypeReference createNormalizedPairType(LightweightTypeReference pairType, LightweightTypeReference mapType, ITypeReferenceOwner owner) { ParameterizedTypeReference result = new ParameterizedTypeReference(owner, pairType.getType()); LightweightTypeReference keyType = mapType.getTypeArguments().get(0); if (keyType.getKind() != LightweightTypeReference.KIND_WILDCARD_TYPE_REFERENCE) { WildcardTypeReference wc = new WildcardTypeReference(owner); wc.addUpperBound(keyType); keyType = wc; } LightweightTypeReference valueType = mapType.getTypeArguments().get(1); if (valueType.getKind() != LightweightTypeReference.KIND_WILDCARD_TYPE_REFERENCE) { WildcardTypeReference wc = new WildcardTypeReference(owner); wc.addUpperBound(valueType); valueType = wc; } result.addTypeArgument(keyType); result.addTypeArgument(valueType); return result; }
if (singleHint.getDeclaredVariance() == VarianceInfo.INVARIANT && singleHint.getSource() == BoundTypeArgumentSource.INFERRED_LATER) { WildcardTypeReference wildcard = resolvedTo.getOwner().newWildcardTypeReference(); wildcard.addUpperBound(resolvedTo); resolvedTo = wildcard; if (constraintTypeRef.getTypeReference().getKind() != LightweightTypeReference.KIND_WILDCARD_TYPE_REFERENCE && constraintTypeRef.getDeclaredVariance() == VarianceInfo.OUT && constraintTypeRef.getActualVariance() == VarianceInfo.INVARIANT) { if (resolvedTo.getKind() == LightweightTypeReference.KIND_WILDCARD_TYPE_REFERENCE && ((WildcardTypeReference) resolvedTo).getLowerBound() != null) { if(resolvedTo.getInvariantBoundSubstitute().isAssignableFrom(constraintTypeRef.getTypeReference())) { WildcardTypeReference wildcard = resolvedTo.getOwner().newWildcardTypeReference(); wildcard.addUpperBound(resolvedTo.getInvariantBoundSubstitute()); resolvedTo = wildcard;
@Override public String getIdentifier() { return getAsString(IdentifierFunction.INSTANCE, false); }
@Override public LightweightTypeReference getLowerBoundSubstitute() { if (lowerBound != null) return lowerBound; return getOwner().newAnyTypeReference(); }