package nl.utwente.viskell.haskell.env; import java.util.ArrayList; import java.util.List; import com.google.common.base.Strings; import nl.utwente.viskell.haskell.type.Type; import nl.utwente.viskell.haskell.type.TypeCon; /** All information about a haskell datatype. */ public class DataTypeInfo { public final class Constructor { /** Haskell constructor name */ private final String name; /** type of the constructor when used as a function */ private final Type type; private Constructor(String name, Type type) { super(); this.name = name; this.type = type; } /** @return the haskell name of the constructor */ public String getName() { return name; } /** @return the type of the constructor when used as a function */ public Type getType() { return type; } /** @return the datatype of which this constructor is part of */ public DataTypeInfo getDataType() { return DataTypeInfo.this; } @Override public String toString() { return this.name + " :: " + this.type.prettyPrint(); } } /** type constructor corresponding to this datatype */ private final TypeCon typecon; /** number of type arguments of this datatype */ private final int typeArity; /** whether this is a builtin datatype and thus can't be matched on */ private final boolean builtin; /** list of data constructors */ private final List<Constructor> constructors; public DataTypeInfo(TypeCon typecon, int typeArity, boolean builtin) { super(); this.typecon = typecon; this.typeArity = typeArity; this.builtin = builtin; this.constructors = new ArrayList<>(); } /** * Add a constructor to this data type * @param name of the constructor * @param type as function of the constructor */ protected void addConstructor(String name, Type type) { this.constructors.add(this.new Constructor(name, type)); } /** @return the type constructor corresponding to this datatype */ public TypeCon getTypecon() { return typecon; } /** @return the number of type arguments of this datatype */ public int getTypeArity() { return typeArity; } /** @return whether this is a builtin datatype and thus can't be matched on */ public boolean isBuiltin() { return builtin; } /** @return the list of all data constructors */ public List<Constructor> getConstructors() { return constructors; } @Override public String toString() { StringBuilder sb = new StringBuilder(); sb.append("data "); sb.append(this.typecon.prettyPrint()); sb.append(" :: "); sb.append(Strings.repeat("* -> ", this.typeArity)); sb.append("*"); if (!this.builtin) { sb.append(" where"); for (Constructor cons : this.constructors) { sb.append("\n\t"); sb.append(cons.toString()); } } return sb.toString(); } }