ProducedTypedReference param = smte.getTargetParameter();
ProducedType paramType = smte.getParameterType();
if (paramType==null && param!=null) {
paramType = param.getFullType();
}
ProducedReference arg = getProducedReference(smte);
if (!smte.getStaticMethodReferencePrimary() &&
dec instanceof Functional &&
param!=null) {
Functional fun = (Functional) dec;
List<ParameterList> apls = fun.getParameterLists();
Declaration pdec = param.getDeclaration();
if (pdec instanceof Functional) {
Functional pfun = (Functional) pdec;
List<ParameterList> ppls = pfun.getParameterLists();
if (apls.isEmpty() || ppls.isEmpty()) {
return null; //TODO: to give a nicer error
}
else {
List<ProducedType> inferredTypes =
new ArrayList<ProducedType>();
List<Parameter> apl = apls.get(0).getParameters();
List<Parameter> ppl = ppls.get(0).getParameters();
for (TypeParameter tp: fun.getTypeParameters()) {
List<ProducedType> list =
new ArrayList<ProducedType>();
for (int i=0; i<apl.size() && i<ppl.size(); i++) {
Parameter ap = apl.get(i);
Parameter pp = ppl.get(i);
ProducedType type =
param.getTypedParameter(pp).getFullType();
ProducedType template =
arg.getTypedParameter(ap).getFullType();
ProducedType it =
inferTypeArg(tp, template, type,
true, false,
new ArrayList<TypeParameter>());
if (it!=null &&
!it.containsTypeParameters()) {
addToUnionOrIntersection(tp, list, it);
}
}
inferredTypes.add(formUnionOrIntersection(tp, list));
}
return inferredTypes;
}
}
}
if (paramType!=null) {
if (unit.isSequentialType(paramType)) {
paramType = unit.getSequentialElementType(paramType);
}
if (unit.isCallableType(paramType)) {
ProducedType template;
if (smte.getStaticMethodReferencePrimary()) {
template = producedType(unit.getTupleDeclaration(),
arg.getType(), arg.getType(),
unit.getEmptyDeclaration().getType());
}
else {
template = unit.getCallableTuple(arg.getFullType());
}
ProducedType type =
unit.getCallableTuple(paramType);
List<ProducedType> inferredTypes =
new ArrayList<ProducedType>();