package typinferenz; import java.util.Iterator; import java.util.Vector; import mycompiler.myclass.Method; import mycompiler.myclass.ParameterList; import typinferenz.assumptions.MethodAssumption; import typinferenz.assumptions.TypeAssumptions; import mycompiler.mytype.GenericTypeVar; import mycompiler.mytype.RefType; import mycompiler.mytype.Type; import mycompiler.mytype.TypePlaceholder; import mycompiler.mytypereconstruction.replacementlistener.CReplaceTypeEvent; import mycompiler.mytypereconstruction.replacementlistener.ITypeReplacementListener; import mycompiler.mytypereconstruction.typeassumption.CMethodTypeAssumption; /** * @see Spezifikation "Complete Typeinference in Java 8" von Martin Plümicke * "interface FunN { R apply(T1 arg1, T2 arg2, ... , TN argN); }" * @author A10023 - Andreas Stadelmeier * */ public class FunN extends RefType implements ITypeReplacementListener{ private Type R; private Vector T; /** * @author Andreas Stadelmeier, a10023 * Benötigt für den Typinferenzalgorithmus für Java 8 * Generiert einen RefType auf eine FunN - Klasse. * @param R * @param T * @return */ public FunN(Type R, Vector T) { super("",null,0); if(T==null || R == null)throw new NullPointerException(); setT(T); setR(R); this.name = "Fun"+T.size();//getName(); } /** * Erstellt eine FunN: * FunN * R und T1 - TparameterCount werden mit TypePlaceholdern besetzt. * @param parameterCount */ public FunN(int parameterCount) { super("",null,0); if(parameterCount<0)throw new RuntimeException("Anzahl der Parameter muss >0 sein"); Vector t = new Vector(); for(int i=0;i t = new Vector(); for(int i=0;i t = new Vector(); if(R!=null)t.add(R); if(T!=null)t.addAll(T); this.set_ParaList(t); } protected void setT(Vector T){ this.T = T; calculateNewParalist(); //ReplacementListener registrieren: for(Type t : T)if(t instanceof TypePlaceholder)((TypePlaceholder)t).addReplacementListener(this); } protected void setR(Type R){ this.R = R; calculateNewParalist(); //Sind die übergebenen Typen TypePlaceholder, so soll die FunN über TypReplacements informiert werden. if(R instanceof TypePlaceholder){ ((TypePlaceholder)R).addReplacementListener(this); } } /* @Override public String getName(){ String ret = "FunN<"+R.toString(); for(Type t : T){ ret += ", " + t.toString(); } ret += ">"; return ret; } */ public void replaceType(CReplaceTypeEvent e) { if(R.equals(e.getOldType()))this.setR(e.getNewType()); for(Type t : T){ if(t.equals(e.getOldType())){ T.setElementAt(e.getNewType(),T.indexOf(t)); this.setT(T); } } } public int getTypeLineNumber() { // TODO Auto-generated method stub return 0; } /* public CMethodTypeAssumption toCMethodTypeAssumption() { //CMethodTypeAssumption ret = new CMethodTypeAssumption(this, "apply", R, this.T.size(), 0,this.getOffset(),new Vector(),null); MethodAssumption ret = null; Method method = new Method(); method.set_Method_Name(this.getName()); ParameterList paraList = new ParameterList(); method.setParameterList(this.get_ParaList().clone()); for(Type t : T){ //ret.addParaAssumption(TypeAssumptions.createCParaTypeAssumption(t.get_Name(), t)); } return ret; } */ @Override public JavaCodeResult printJavaCode(ResultSet resultSet){ //String ret = super.printJavaCode(resultSet) + (T!=null ? this.T.size() : 0) +"<"; JavaCodeResult ret = new JavaCodeResult("Fun" + (T!=null ? this.T.size() : 0) +"<"); ret .attach( this.R.printJavaCode(resultSet)).attach(", "); Iterator it = T.iterator(); while(it.hasNext()){ Type t = it.next(); ret.attach( t.printJavaCode(resultSet)); if(it.hasNext())ret.attach(", "); } //ret = ret.substring(0, ret.length()-2); return ret.attach(">"); } /** * Die Clone-Methode von RefType darf von FunN NICHT überschrieben werden. @Override public FunN clone() { FunN ret = null; Vector clonepara = new Vector(); for(int i = 0; i< this.T.size(); i++) { clonepara.addElement(((Type)this.T.elementAt(i)).clone()); } ret = new FunN(this.R.clone(),clonepara); ret.setPrimitiveFlag(this.getPrimitiveFlag()); return ret; } */ }