package jetbrains.mps.baseLanguage.behavior; /*Generated by MPS */ import java.util.Map; import java.util.List; import org.jetbrains.mps.openapi.model.SNode; import java.util.Set; import java.util.ArrayList; import jetbrains.mps.internal.collections.runtime.MapSequence; import jetbrains.mps.internal.collections.runtime.ListSequence; import jetbrains.mps.internal.collections.runtime.SetSequence; import jetbrains.mps.baseLanguage.scopes.ClassifierScopeUtils; import jetbrains.mps.lang.smodel.generator.smodelAdapter.SNodeOperations; import jetbrains.mps.smodel.adapter.structure.MetaAdapterFactory; import jetbrains.mps.internal.collections.runtime.Sequence; import jetbrains.mps.internal.collections.runtime.IWhereFilter; import java.util.HashMap; import jetbrains.mps.lang.smodel.generator.smodelAdapter.SPropertyOperations; import jetbrains.mps.lang.smodel.generator.smodelAdapter.SLinkOperations; import java.util.HashSet; import org.jetbrains.mps.openapi.language.SAbstractConcept; import jetbrains.mps.baseLanguage.scopes.GenericTypesUtil; public final class MethodOverrideHelper { private Map<String, List<SNode>> myMethodsByName; private Map<SNode, List<SNode>> myOverriddenMethods; private Set<SNode> myDependsOnNodes; public MethodOverrideHelper(SNode classifier) { init(classifier); } public List<SNode> getMethods() { List<SNode> result = new ArrayList<SNode>(); for (List<SNode> list : MapSequence.fromMap(this.myMethodsByName).values()) { ListSequence.fromList(result).addSequence(ListSequence.fromList(list)); } return result; } public List<SNode> getOverriddenMethods(SNode method) { List<SNode> list = MapSequence.fromMap(this.myOverriddenMethods).get(method); if (list != null) { return list; } return new ArrayList<SNode>(); } private void init(SNode classifier) { Iterable<SNode> classifiers = SetSequence.fromSet(ClassifierScopeUtils.getExtendedClassifiers(classifier)).toListSequence(); Iterable<SNode> interfaces = SNodeOperations.ofConcept(classifiers, MetaAdapterFactory.getConcept(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0x101edd46144L, "jetbrains.mps.baseLanguage.structure.Interface")); Iterable<SNode> nonInterfaces = Sequence.fromIterable(classifiers).where(new IWhereFilter<SNode>() { public boolean accept(SNode it) { return !(SNodeOperations.isInstanceOf(it, MetaAdapterFactory.getConcept(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0x101edd46144L, "jetbrains.mps.baseLanguage.structure.Interface"))); } }); classifiers = Sequence.fromIterable(nonInterfaces).union(Sequence.fromIterable(interfaces)); List<SNode> allMethods = new ArrayList<SNode>(); for (SNode currentClassifier : classifiers) { ListSequence.fromList(allMethods).addSequence(Sequence.fromIterable(Classifier__BehaviorDescriptor.methods_id4_LVZ3pBKCn.invoke(currentClassifier))); } this.myMethodsByName = MapSequence.fromMap(new HashMap<String, List<SNode>>()); this.myOverriddenMethods = MapSequence.fromMap(new HashMap<SNode, List<SNode>>()); forEachInAllMethods: for (SNode currMethod : allMethods) { String name = SPropertyOperations.getString(currMethod, MetaAdapterFactory.getProperty(0xceab519525ea4f22L, 0x9b92103b95ca8c0cL, 0x110396eaaa4L, 0x110396ec041L, "name")); if (name == null) { name = ""; } if (!(MapSequence.fromMap(this.myMethodsByName).containsKey(name))) { List<SNode> methods = new ArrayList<SNode>(); methods.add(currMethod); MapSequence.fromMap(myMethodsByName).put(name, methods); MapSequence.fromMap(myOverriddenMethods).put(currMethod, new ArrayList<SNode>()); } else { int currMethodParmCount = ListSequence.fromList(SLinkOperations.getChildren(currMethod, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1feL, "parameter"))).count(); List<SNode> equalParmCountMethods = new ArrayList<SNode>(); List<SNode> methods = MapSequence.fromMap(this.myMethodsByName).get(name); for (SNode method : methods) { if ((SNodeOperations.getParent(currMethod) != SNodeOperations.getParent(method)) && ListSequence.fromList(SLinkOperations.getChildren(method, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1feL, "parameter"))).count() == currMethodParmCount) { equalParmCountMethods.add(method); } } if (equalParmCountMethods.size() > 0) { if (currMethodParmCount == 0) { ListSequence.fromList(MapSequence.fromMap(myOverriddenMethods).get(ListSequence.fromList(equalParmCountMethods).first())).addElement(currMethod); continue forEachInAllMethods; } Map<SNode, SNode> typeByTypeVar = ClassifierScopeUtils.resolveClassifierTypeVars(classifier); String currentParms = this.createMethodParameterTypesString(currMethod, typeByTypeVar); for (SNode otherMethod : equalParmCountMethods) { String otherParms = this.createMethodParameterTypesString(otherMethod, typeByTypeVar); if (otherParms.equals(currentParms)) { MapSequence.fromMap(this.myOverriddenMethods).get(otherMethod).add(currMethod); continue forEachInAllMethods; } } } ListSequence.fromList(MapSequence.fromMap(myMethodsByName).get(name)).addElement(currMethod); MapSequence.fromMap(myOverriddenMethods).put(currMethod, new ArrayList<SNode>()); } } this.myDependsOnNodes = SetSequence.fromSet(new HashSet<SNode>()); for (SNode currentClassifier : classifiers) { SetSequence.fromSet(this.myDependsOnNodes).addElement(currentClassifier); } for (SNode method : allMethods) { SetSequence.fromSet(this.myDependsOnNodes).addElement(method); for (SNode parm : SLinkOperations.getChildren(method, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1feL, "parameter"))) { SNode type = SLinkOperations.getTarget(parm, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0x450368d90ce15bc3L, 0x4ed4d318133c80ceL, "type")); if (type == null) { continue; } SetSequence.fromSet(myDependsOnNodes).addElement(type); SetSequence.fromSet(myDependsOnNodes).addSequence(ListSequence.fromList(SNodeOperations.getNodeDescendants(type, null, false, new SAbstractConcept[]{}))); } } } private String createMethodParameterTypesString(SNode method, Map<SNode, SNode> typeByTypeVar) { StringBuilder result = new StringBuilder(); for (SNode parm : SLinkOperations.getChildren(method, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0xf8cc56b1fcL, 0xf8cc56b1feL, "parameter"))) { SNode type = SLinkOperations.getTarget(parm, MetaAdapterFactory.getContainmentLink(0xf3061a5392264cc5L, 0xa443f952ceaf5816L, 0x450368d90ce15bc3L, 0x4ed4d318133c80ceL, "type")); type = GenericTypesUtil.getTypeWithResolvedTypeVars(type, typeByTypeVar); if (result.length() > 0) { result.append(','); } if (type != null) { result.append(Type__BehaviorDescriptor.getErasureSignature_idhEwIzNx.invoke(type)); } else { result.append(""); } } return result.toString(); } }