Fixed type substitution for constructor calls

This commit is contained in:
Andrey Breslav
2011-05-03 13:10:58 +04:00
parent e46792a80e
commit 9f0d0e8722
3 changed files with 41 additions and 48 deletions
@@ -29,7 +29,7 @@ public class ConstructorDescriptorImpl extends FunctionDescriptorImpl implements
}
public ConstructorDescriptor initialize(@NotNull List<ValueParameterDescriptor> unsubstitutedValueParameters) {
super.initialize(Collections.<TypeParameterDescriptor>emptyList(), unsubstitutedValueParameters, JetStandardClasses.getNothingType());
super.initialize(Collections.<TypeParameterDescriptor>emptyList(), unsubstitutedValueParameters, getContainingDeclaration().getDefaultType());
return this;
}
@@ -61,9 +61,11 @@ public class ConstructorDescriptorImpl extends FunctionDescriptorImpl implements
return Collections.emptyList();
}
@NotNull
@Override
public JetType getUnsubstitutedReturnType() {
return getContainingDeclaration().getDefaultType();
protected FunctionDescriptorImpl createSubstitutedCopy() {
return new ConstructorDescriptorImpl(
this,
Collections.<Attribute>emptyList(), // TODO
isPrimary);
}
}
@@ -3,6 +3,7 @@ package org.jetbrains.jet.lang.types;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Collections;
import java.util.List;
/**
@@ -78,8 +79,37 @@ public class FunctionDescriptorImpl extends DeclarationDescriptorImpl implements
}
@Override
public FunctionDescriptor substitute(TypeSubstitutor substitutor) {
return FunctionDescriptorUtil.substituteFunctionDescriptor(this, substitutor);
public final FunctionDescriptor substitute(TypeSubstitutor substitutor) {
if (substitutor.isEmpty()) {
return this;
}
FunctionDescriptorImpl substitutedDescriptor;
substitutedDescriptor = createSubstitutedCopy();
List<ValueParameterDescriptor> substitutedValueParameters = FunctionDescriptorUtil.getSubstitutedValueParameters(substitutedDescriptor, this, substitutor);
if (substitutedValueParameters == null) {
return null;
}
JetType substitutedReturnType = FunctionDescriptorUtil.getSubstitutedReturnType(this, substitutor);
if (substitutedReturnType == null) {
return null;
}
substitutedDescriptor.initialize(
Collections.<TypeParameterDescriptor>emptyList(), // TODO : questionable
substitutedValueParameters,
substitutedReturnType
);
return substitutedDescriptor;
}
protected FunctionDescriptorImpl createSubstitutedCopy() {
return new FunctionDescriptorImpl(
this,
// TODO : safeSubstitute
getAttributes(),
getName());
}
@Override
@@ -58,7 +58,7 @@ public class FunctionDescriptorUtil {
}
@Nullable
private static List<ValueParameterDescriptor> getSubstitutedValueParameters(FunctionDescriptor substitutedDescriptor, @NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
public static List<ValueParameterDescriptor> getSubstitutedValueParameters(FunctionDescriptor substitutedDescriptor, @NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
List<ValueParameterDescriptor> result = new ArrayList<ValueParameterDescriptor>();
List<ValueParameterDescriptor> unsubstitutedValueParameters = functionDescriptor.getUnsubstitutedValueParameters();
for (int i = 0, unsubstitutedValueParametersSize = unsubstitutedValueParameters.size(); i < unsubstitutedValueParametersSize; i++) {
@@ -81,53 +81,14 @@ public class FunctionDescriptorUtil {
}
@Nullable
private static JetType getSubstitutedReturnType(@NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
public static JetType getSubstitutedReturnType(@NotNull FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
return substitutor.substitute(functionDescriptor.getUnsubstitutedReturnType(), Variance.OUT_VARIANCE);
}
@Nullable
public static FunctionDescriptor substituteFunctionDescriptor(@NotNull List<JetType> typeArguments, @NotNull FunctionDescriptor functionDescriptor) {
Map<TypeConstructor, TypeProjection> substitutionContext = createSubstitutionContext(functionDescriptor, typeArguments);
return substituteFunctionDescriptor(functionDescriptor, TypeSubstitutor.create(substitutionContext));
}
@Nullable
public static FunctionDescriptor substituteFunctionDescriptor(FunctionDescriptor functionDescriptor, TypeSubstitutor substitutor) {
if (substitutor.isEmpty()) {
return functionDescriptor;
}
FunctionDescriptorImpl substitutedDescriptor;
if (functionDescriptor instanceof ConstructorDescriptor) {
ConstructorDescriptor original = (ConstructorDescriptor) functionDescriptor;
substitutedDescriptor = new ConstructorDescriptorImpl(
original, functionDescriptor.getAttributes(), original.isPrimary()
);
}
else {
substitutedDescriptor = new FunctionDescriptorImpl(
functionDescriptor,
// TODO : safeSubstitute
functionDescriptor.getAttributes(),
functionDescriptor.getName());
}
List<ValueParameterDescriptor> substitutedValueParameters = getSubstitutedValueParameters(substitutedDescriptor, functionDescriptor, substitutor);
if (substitutedValueParameters == null) {
return null;
}
JetType substitutedReturnType = getSubstitutedReturnType(functionDescriptor, substitutor);
if (substitutedReturnType == null) {
return null;
}
substitutedDescriptor.initialize(
Collections.<TypeParameterDescriptor>emptyList(), // TODO : questionable
substitutedValueParameters,
substitutedReturnType
);
return substitutedDescriptor;
return functionDescriptor.substitute(TypeSubstitutor.create(substitutionContext));
}
@NotNull