The StaDyn Programming Language
Source code documentation of StaDyn, a hybrid static and dynamic typing language.
TypeVariable.cs
Go to the documentation of this file.
1 // -------------------------------------------------------------------------- //
3 // Project rROTOR //
4 // -------------------------------------------------------------------------- //
5 // File: TypeVariable.cs //
6 // Authors: Cristina Gonzalez Muņoz - cristi.gm@gmail.com //
7 // Francisco Ortin - francisco.ortin@gmail.com //
8 // Description: //
9 // Represents a generic type expression. //
10 // Inheritance: TypeExpression. //
11 // Implements Composite pattern [Leaf]. //
12 // -------------------------------------------------------------------------- //
13 // Create date: 15-10-2006 //
14 // Modification date: 27-03-2007 //
16 //VISTO
17 using System;
18 using System.Collections.Generic;
19 using System.Text;
20 
21 using AST;
22 using ErrorManagement;
23 using TypeSystem.Constraints;
24 using Tools;
25 using DynVarManagement;
26 using TypeSystem.Operations;
27 
28 namespace TypeSystem {
36  public class TypeVariable : TypeExpression {
37 
38  #region Fields
39 
43  private static int lastVariable = 0;
44 
48  private static TypeVariable lastTypeVariable;
49 
53  private int variable;
54 
58  private EquivalenceClass equivalenceClass;
59 
60  #endregion
61 
62  #region Properties
63 
67  public static TypeVariable NewTypeVariable {
68  get {
69  // * Creates a new type variable
70  TypeVariable typeVariable = new TypeVariable(lastVariable++);
71  // * And registers it into the type table
72  TypeTable.Instance.AddVarType(typeVariable);
73  TypeVariable.lastTypeVariable = typeVariable;
74  return typeVariable;
75  }
76  }
77 
82  get { return lastTypeVariable; }
83  }
84 
89  get { return equivalenceClass; }
90  set { equivalenceClass = value; }
91  }
92 
96  public int Variable {
97  get { return this.variable; }
98  }
99 
104  get {
105  if (CheckRecursion())
106  return null;
107  if (this.equivalenceClass != null)
108  return this.equivalenceClass.Substitution;
109  return null;
110  }
111  }
116  private bool CheckRecursion()
117  {
118  IList<TypeExpression> teList = new List<TypeExpression>();
119  if (this.equivalenceClass == null)
120  return false;
121  TypeExpression substitution = this.equivalenceClass.Substitution;
122  if (substitution == null)
123  return false;
124  teList.Add(this);
125  if (substitution is UnionType)
126  return CheckRecursion(substitution as UnionType, teList);
127  else if (substitution is TypeVariable)
128  return CheckRecursion(substitution as TypeVariable, teList);
129  else
130  return false;
131  }
132 
133  private bool CheckRecursion(UnionType ut, IList<TypeExpression> teList)
134  {
135  foreach (var typeSet in ut.TypeSet)
136  {
137  if (typeSet is TypeVariable && CheckRecursion(typeSet as TypeVariable, teList))
138  return true;
139  }
140  return false;
141  }
142 
143  private bool CheckRecursion(TypeVariable tv, IList<TypeExpression> teList)
144  {
145  if (teList.Contains(tv))
146  return true;
147  else
148  {
149  if (tv.equivalenceClass == null)
150  return false;
151  TypeExpression substitution = tv.equivalenceClass.Substitution;
152  if (substitution == null)
153  return false;
154  teList.Add(tv);
155  if (substitution is UnionType)
156  return CheckRecursion(substitution as UnionType,teList);
157  else if (substitution is TypeVariable)
158  return CheckRecursion(substitution as TypeVariable,teList);
159  else
160  return false;
161  }
162  }
163 
164 
165 
169  public override string FullName {
170  get {
171  this.BuildFullName();
172  return this.fullName;
173  }
174  }
175 
179  public override bool IsDynamic {
180  set {
181  // * If type variable is dynamic, so it is its substitution
182  this.isDynamic = value;
183  if (this.Substitution != null)
184  this.Substitution.IsDynamic = value;
185  }
186  }
187  #endregion
188 
189  #region Constructor
190 
195  private TypeVariable(int variable) {
196  this.variable = variable;
197  this.BuildFullName();
198  this.BuildTypeExpressionString(TypeExpression.MAX_DEPTH_LEVEL_TYPE_EXPRESSION);
199  this.ValidTypeExpression = true;
200  }
201 
202  #endregion
203 
204  #region addToMyEquivalenceClass()
205  internal bool addToMyEquivalenceClass(TypeExpression typeExpression, SortOfUnification unification, IList<Pair<TypeExpression, TypeExpression>> previouslyUnified) {
214  // * It the type variable does not have a equivalence class, we create it
215  if (this.equivalenceClass == null)
216  this.equivalenceClass = new EquivalenceClass(this);
217  bool added = this.equivalenceClass.add(typeExpression, unification, previouslyUnified);
218  this.ValidTypeExpression = false;
219  if (typeExpression is TypeVariable)
220  typeExpression.ValidTypeExpression = false;
221  return added;
222  }
223 
224  #endregion
225 
226  #region BuildTypeExpressionString()
227  public override string BuildTypeExpressionString(int depthLevel) {
232  if (this.ValidTypeExpression) return this.typeExpression;
233  if (depthLevel <= 0) return this.FullName;
234 
235  if (equivalenceClass == null)
236  return this.typeExpression = "Var(" + this.variable + ")";
237  string substitutionString, eqClassString;
238  eqClassString = equivalenceClass.ToString();
239  if (equivalenceClass.Substitution == null)
240  substitutionString = "fresh variable";
241  else
242  substitutionString = equivalenceClass.Substitution.BuildTypeExpressionString(depthLevel - 1);
243  this.ValidTypeExpression = true;
244  return this.typeExpression = String.Format("[Var({0})={1}={2}]", this.variable, eqClassString, substitutionString);
245  }
246  #endregion
247 
248  #region BuildFullName()
249  public override void BuildFullName() {
253  if (equivalenceClass == null) {
254  this.fullName = "Var(" + this.variable + ")";
255  return;
256  }
257  string eqClassString = equivalenceClass.ToString();
258  if (equivalenceClass.Substitution == null)
259  this.fullName = String.Format("[Var({0})={1}]", this.variable, eqClassString);
260  else
261  this.fullName = String.Format("[Var({0})={1}={2}]", this.variable, eqClassString, equivalenceClass.Substitution.FullName);
262  }
263  #endregion
264 
265  #region ToString()
266 
267  public override string ToString() {
268  this.validTypeExpression = false;
269  return this.typeExpression = this.BuildTypeExpressionString(1);
270  }
271 
272  #endregion
273 
274  #region Equivalent() ANULADA
275  #endregion
290 
291  // WriteType Inference
292 
293  #region Dispatcher
294  public override object AcceptOperation(TypeSystemOperation op, object arg)
295  {
296  return op.Exec(this, arg);
297  }
298  #endregion
299 
300  #region Dot() ANULADA
301  //public override TypeExpression Dot(string field, MethodType methodAnalyzed, IList<TypeExpression> previousDot, Location location) {
312  // if (this.Substitution != null) {
313  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
314  // return this.Substitution.Dot(field, methodAnalyzed, previousDot, location);
315  // }
316  // if (methodAnalyzed != null) {
317  // // * A attribute access constraint is added to the method analyzed
318  // DotConstraint constraint = new DotConstraint(this, field, location);
319  // methodAnalyzed.AddConstraint(constraint);
320  // return constraint.ReturnType;
321  // }
322  // ErrorManager.Instance.NotifyError(new OperationNotAllowedError(".", this.fullName, location));
323  // return null;
324  //}
331  //public override TypeExpression Dot(string memberName, IList<TypeExpression> previousDot) {
332  // if (this.Substitution != null) {
333  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
334  // return this.Substitution.Dot(memberName, previousDot);
335  // }
336  // return null;
337  //}
338  #endregion
339 
340  #region Parenthesis() ANULADA
341  //public override TypeExpression Parenthesis(TypeExpression actualImplicitObject, TypeExpression[] arguments, MethodType methodAnalyzed,
354  // SortOfUnification activeSortOfUnification, Location location) {
355  // if (this.Substitution != null) {
356  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
357  // return this.Substitution.Parenthesis(actualImplicitObject, arguments, methodAnalyzed, activeSortOfUnification, location);
358  // }
359  // if (methodAnalyzed != null) {
360  // // * A method invocation constraint is added to the method analyzed
361  // ParenthesisConstraint constraint = new ParenthesisConstraint(this, actualImplicitObject, arguments, activeSortOfUnification, location);
362  // methodAnalyzed.AddConstraint(constraint);
363  // return constraint.ReturnType;
364  // }
365  // ErrorManager.Instance.NotifyError(new OperationNotAllowedError("()", this.fullName, location));
366  // return null;
367  //}
368 
369  #endregion
370 
371  #region Assignment() ANULADA
372  //public override TypeExpression Assignment(TypeExpression operand, AssignmentOperator op, MethodType methodAnalyzed, SortOfUnification unification,
386  // TypeExpression actualImplicitObject, Location location) {
387  // // * Bounded variable?
388  // if (this.Substitution != null && unification == SortOfUnification.Equivalent)
389  // // * Check promotion to its substitution
390  // return operand.Promotion(this, op, methodAnalyzed, location);
391  // // * If the variable its not bounded, we add the parameter to the equivalence list
392  // if (this.addToMyEquivalenceClass(operand, unification, new List<Pair<TypeExpression, TypeExpression>>()))
393  // return this;
394  // // * If it has not been possible, error
395  // ErrorManager.Instance.NotifyError(new OperationNotAllowedError(op.ToString(), this.FullName, operand.FullName, location));
396  // return null;
397  //}
398  #endregion
399 
400  #region Bracket() ANULADA
401  //public override TypeExpression Bracket(TypeExpression index, MethodType methodAnalyzed, bool showErrorMessage, Location location) {
412  // if (this.Substitution != null) {
413  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
414  // return this.Substitution.Bracket(index, methodAnalyzed, showErrorMessage, location);
415  // }
416  // if (methodAnalyzed != null) {
417  // // * A bracket constraint is added to the method analyzed
418  // SquareBracketConstraint bracketConstraint = new SquareBracketConstraint(this, index, location);
419  // methodAnalyzed.AddConstraint(bracketConstraint);
420  // // * Also a promotion constriaint of the index to IntType
421  // //index.Promotion(IntType.Instance, ArrayOperator.Indexer, methodAnalyzed, fileName, line, column);
422  // return bracketConstraint.ReturnType;
423  // }
424  // if (showErrorMessage)
425  // ErrorManager.Instance.NotifyError(new OperationNotAllowedError("[]", this.fullName, location));
426  // return null;
427  //}
428  #endregion
429 
430  #region Arithmetic RELATIONQL() ANULADA
431 /* /// <summary>
442  public override TypeExpression Arithmetic(TypeExpression operand, Enum op, MethodType methodAnalyzed, bool showErrorMessage, Location location) {
443  if (this.Substitution != null) {
444  DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
445  return this.Substitution.Arithmetic(operand, op, methodAnalyzed, showErrorMessage, location);
446  }
447  if (methodAnalyzed != null) {
448  // * A constraint is added to the method analyzed
449  ArithmeticConstraint constraint = new ArithmeticConstraint(this, operand, op, location);
450  methodAnalyzed.AddConstraint(constraint);
451  return constraint.ReturnType;
452  }
453  if (showErrorMessage)
454  ErrorManager.Instance.NotifyError(new OperationNotAllowedError(op.ToString(), this.fullName, operand.FullName, location));
455  return null;
456  }
467  public override TypeExpression Arithmetic(UnaryOperator op, MethodType methodAnalyzed, bool showErrorMessage, Location location) {
468  if (this.Substitution != null) {
469  DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
470  return this.Substitution.Arithmetic(op, methodAnalyzed, showErrorMessage, location);
471  }
472  if (methodAnalyzed != null) {
473  // * A constraint is added to the method analyzed
474  ArithmeticConstraint constraint = new ArithmeticConstraint(this, op, location);
475  methodAnalyzed.AddConstraint(constraint);
476  return constraint.ReturnType;
477  }
478  if (showErrorMessage)
479  ErrorManager.Instance.NotifyError(new OperationNotAllowedError(op.ToString(), this.fullName, location));
480  return null;
481  }
482  #endregion
483 
484  #region Relational()
496  public override TypeExpression Relational(TypeExpression operand, RelationalOperator op, MethodType methodAnalyzed, bool showErrorMessage, Location location) {
497  if (this.Substitution != null) {
498  DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
499  return this.Substitution.Relational(operand, op, methodAnalyzed, showErrorMessage, location);
500  }
501  if (methodAnalyzed != null) {
502  // * A constraint is added to the method analyzed
503  RelationalConstraint constraint = new RelationalConstraint(this, operand, op, location);
504  methodAnalyzed.AddConstraint(constraint);
505  return constraint.ReturnType;
506  }
507  if (showErrorMessage)
508  ErrorManager.Instance.NotifyError(new OperationNotAllowedError(op.ToString(), this.fullName, operand.fullName, location));
509  return null;
510  }
511 */
512  #endregion
513 
514  // WriteType Promotion
515 
516  #region PromotionLevel() ANULADA
517  //public override int PromotionLevel(TypeExpression type) {
523  // if (this.Substitution != null) {
524  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
525  // // * If the variable is bounded, the promotion is the one of its substitution
526  // return this.EquivalenceClass.Substitution.PromotionLevel(type);
527  // }
528  // // * A free variable is complete promotion
529  // return 0;
530  //}
531 
532  #endregion
533 
534  #region Promotion() ANULADA
535  //public override TypeExpression Promotion(TypeExpression type, MethodType methodAnalyzed, Location location) {
546  // if (this.Substitution != null) {
547  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
548  // return this.Substitution.Promotion(type, methodAnalyzed, location);
549  // }
550  // if (methodAnalyzed != null) {
551  // // * A constraint is added to the method analyzed
552  // PromotionConstraint constraint = new PromotionConstraint(this, type, location);
553  // methodAnalyzed.AddConstraint(constraint);
554  // return constraint.ReturnType;
555  // }
556  // ErrorManager.Instance.NotifyError(new TypePromotionError(this.FullName, type.FullName, location));
557  // return null;
558  //}
559  //public override TypeExpression Promotion(TypeExpression type, Enum op, MethodType methodAnalyzed, Location location) {
560  // if (this.Substitution != null) {
561  // DynVarOptions.Instance.AssignDynamism(this.Substitution, this.IsDynamic);
562  // return this.Substitution.Promotion(type, op, methodAnalyzed, location);
563  // }
564  // if (methodAnalyzed != null) {
565  // // * A constraint is added to the method analyzed
566  // PromotionConstraint constraint = new PromotionConstraint(this, type, op, location);
567  // methodAnalyzed.AddConstraint(constraint);
568  // return constraint.ReturnType;
569  // }
570  // ErrorManager.Instance.NotifyError(new TypePromotionError(this.FullName, type.FullName, op.ToString(), location));
571  // return null;
572  //}
573  #endregion
574 
575  #region Cast() ANULADA
576  //public override TypeExpression Cast(TypeExpression castType, MethodType methodAnalyzed, Location location) {
586  // if (this.Substitution != null) {
587  // return this.Substitution.Cast(castType, methodAnalyzed, location);
588  // }
589  // if (methodAnalyzed != null) {
590  // // * A constraint is added to the method analyzed
591  // CastConstraint constraint = new CastConstraint(this, castType, location);
592  // methodAnalyzed.AddConstraint(constraint);
593  // return constraint.ReturnType;
594  // }
595  // ErrorManager.Instance.NotifyError(new TypeCastError(this.FullName, castType.FullName, location));
596  // return null;
597  //}
598  #endregion
599 
600  #region EqualsForOverload() ANULADA
601  //public override bool EqualsForOverload(object typeExpression) {
607  // return typeExpression is TypeVariable;
608  //}
609  #endregion
610 
611  // WriteType Unification
612 
613  #region Unify
614  public override bool Unify(TypeExpression te, SortOfUnification unification, IList<Pair<TypeExpression, TypeExpression>> previouslyUnified) {
622  if (te == null)
623  return false;
624  bool success = this.addToMyEquivalenceClass(te, unification, previouslyUnified);
625  // * Clears the type expression cache
626  this.ValidTypeExpression = te.ValidTypeExpression = false;
627  return success;
628  }
629  #endregion
630 
631  #region HasTypeVariables()
632  public override bool HasTypeVariables() {
638  return true;
639  }
640  #endregion
641 
642  #region IsFressVariable()
643  public override bool IsFreshVariable() {
648  return this.Substitution == null;
649  }
650  #endregion
651 
652  #region CloneType()
653  public override TypeExpression CloneType(IDictionary<TypeVariable, TypeVariable> typeVariableMappings) {
662  // * We clone the type of the elements
663  IList<EquivalenceClass> equivalenceClasses = new List<EquivalenceClass>();
664  TypeVariable newTypeVariable = (TypeVariable)this.CloneTypeVariables(typeVariableMappings, equivalenceClasses, new List<ClassType>());
665  // * For each equivalence class we create a new one,
666  // substituting the old type variables for the new ones
667  // * The substitution is not altered
668  // * Since equivalence classes and type variables have a bidirectional association,
669  // the new equivalence classes will make type variables update their new equivalence classes
670  foreach (EquivalenceClass equivalenceClass in equivalenceClasses)
671  equivalenceClass.UpdateEquivalenceClass(typeVariableMappings);
672  newTypeVariable.ValidTypeExpression = false;
673  // * The new class type is returned
674  return newTypeVariable;
675  }
676  #endregion
677 
678  #region CloneTypeVariables()
679  public override TypeExpression CloneTypeVariables(IDictionary<TypeVariable, TypeVariable> typeVariableMappings, IList<EquivalenceClass> equivalenceClasses, IList<ClassType> clonedClasses) {
691  // * If the variable to be cloned already has a map, we return the latter
692  if (typeVariableMappings.ContainsKey(this))
693  return typeVariableMappings[this];
694  TypeVariable newOne = TypeVariable.NewTypeVariable;
695  newOne.IsDynamic = this.IsDynamic;
696  // * Sets the mapping between the old and new one in the typeVariableMappings parameter
697  typeVariableMappings[this] = newOne;
698  // * Add both equivalence classes to the equivalenceClasses parameter
699  if (this.EquivalenceClass != null && !equivalenceClasses.Contains(this.equivalenceClass))
700  equivalenceClasses.Add(this.equivalenceClass);
701  // * Assigns a clone of the substitution when it previously exists
702  if (this.Substitution != null) {
703  TypeExpression clonedSubstitution = this.Substitution.CloneTypeVariables(typeVariableMappings, equivalenceClasses, clonedClasses);
704  newOne.addToMyEquivalenceClass(clonedSubstitution, SortOfUnification.Equivalent, new List<Pair<TypeExpression, TypeExpression>>());
705  }
706  else if (this.EquivalenceClass != null)
707  newOne.equivalenceClass = this.equivalenceClass;
708  newOne.ValidTypeExpression = false;
709  // * Returns the new type variable
710  return newOne;
711  }
712  #endregion
713 
714  #region UpdateEquivalenceClass()
715  public override void UpdateEquivalenceClass(IDictionary<TypeVariable, TypeVariable> typeVariableMappings, IList<TypeExpression> previouslyUpdated) {
722  // * Checks infinite loops
723  if (previouslyUpdated.Contains(this))
724  return;
725  previouslyUpdated.Add(this);
726 
727  // * Updates the equivalence class
728  if (this.Substitution == null)
729  return;
730  this.Substitution.UpdateEquivalenceClass(typeVariableMappings, previouslyUpdated);
731  this.ValidTypeExpression = false;
732  }
733  #endregion
734 
735  #region Freeze()
736  public override TypeExpression Freeze()
743  {
744  if (this.Substitution == null)
745  return this;
746  return this.Substitution.Freeze();
747  }
748 
749  public TypeExpression Freeze(IList<TypeExpression> evaluated)
750  {
751  if (this.Substitution == null)
752  return this;
753  if (this.Substitution is TypeVariable)
754  return ((TypeVariable)this.Substitution).Freeze(evaluated);
755  else if (this.Substitution is UnionType)
756  return ((UnionType)this.Substitution).Freeze(evaluated);
757  return this.Substitution.Freeze();
758  }
759 
760  #endregion
761 
762  // SSA
763 
764  #region Clone()
765  internal override TypeExpression Clone(IDictionary<int, TypeVariable> clonedTypeVariables, IList<EquivalenceClass> equivalenceClasses, MethodType methodAnalyzed) {
776  if (clonedTypeVariables.ContainsKey(this.variable))
777  // * Already cloned
778  return clonedTypeVariables[this.variable];
779  if (this.Substitution != null) {
780  // * Lets clone it
781  TypeVariable newTypeVariable = (TypeVariable)this.MemberwiseClone();
782  newTypeVariable.variable = TypeVariable.NewTypeVariable.Variable;
783  // * We add it to the list
784  clonedTypeVariables[this.variable] = newTypeVariable;
785  // * We also clone all the type variables of its class equivalence
786  if (newTypeVariable.equivalenceClass != null)
787  newTypeVariable.equivalenceClass.CloneTypeVariables(clonedTypeVariables, equivalenceClasses, methodAnalyzed);
788  newTypeVariable.BuildFullName();
789  newTypeVariable.BuildTypeExpressionString(2);
790  return newTypeVariable;
791  }
792  if (methodAnalyzed != null) {
793  // * A clone constraint is added to the method analyzed
794  CloneConstraint constraint = new CloneConstraint(this);
795  methodAnalyzed.AddConstraint(constraint);
796  // * We add it to the list
797  clonedTypeVariables[this.variable] = constraint.ReturnType;
798  // * We also clone all the type variables of its class equivalence
799  if (this.equivalenceClass != null)
800  this.equivalenceClass.CloneTypeVariables(clonedTypeVariables, equivalenceClasses, methodAnalyzed);
801  return constraint.ReturnType;
802  }
803  return null;
804  }
805  #endregion
806 
807  #region Equals&GetHashCode()
808  public override bool Equals(object obj) {
809  if (this.GetHashCode() != obj.GetHashCode())
810  return false;
811  TypeVariable typeVariable = obj as TypeVariable;
812  if (typeVariable == null)
813  return false;
814  return this.variable == typeVariable.variable;
815  }
816  public override int GetHashCode() {
817  return this.variable;
818  }
819  #endregion
820 
821  // Loop Detection
822 
823  #region Remove()
824  public override bool Remove(TypeVariable toRemove) {
831  bool ret = this.equivalenceClass.Remove(toRemove);
832  this.ValidTypeExpression = false;
833  return ret;
834  }
835  #endregion
836 
837  // Code Generation
838 
839  #region ILType()
840  public override string ILType() {
845  // * If the type variable has been unified, the IL type is the substitution
846  if (this.Substitution != null)
847  return this.Substitution.ILType();
848  // * Otherwise, object is used
849  return "object";
850  }
851  #endregion
852 
853  #region IsValueType()
854  public override bool IsValueType() {
859  if (this.Substitution != null)
860  return this.Substitution.IsValueType();
861  return false;
862  }
863 
864  public bool IsValueType(IList<TypeExpression> evaluated)
865  {
866  if (this.Substitution != null)
867  {
868  if (this.Substitution is UnionType)
869  return ((UnionType) this.Substitution).IsValueType(evaluated);
870  if(this.Substitution is TypeVariable)
871  return ((TypeVariable) this.Substitution).IsValueType(evaluated);
872  return this.Substitution.IsValueType();
873  }
874  return false;
875  }
876 
877  #endregion
878 
879  }
880 }
881 
bool IsValueType(IList< TypeExpression > evaluated)
static TypeVariable NewTypeVariable
Gets a new identify to the variable type
Definition: TypeVariable.cs:67
override int GetHashCode()
override TypeExpression CloneTypeVariables(IDictionary< TypeVariable, TypeVariable > typeVariableMappings, IList< EquivalenceClass > equivalenceClasses, IList< ClassType > clonedClasses)
Method that clones each type variable of a type expression. Equivalence classes are not cloned (but i...
override string FullName
The full name in type variables is calculated just in time
Representa a union type.
Definition: UnionType.cs:36
TypeExpression Substitution
A equivalence class could be bounded to a unique no variable type
override void BuildFullName()
Creates/Updates the full name of the type expression
override bool IsValueType()
True if type expression is a ValueType. Otherwise, false.
override string ILType()
Gets the type name to use in IL code.
This class represent the entry wnen sending a message to an operation object derived from TypeExpress...
override bool IsFreshVariable()
To know if it is a type variable with no substitution
static TypeVariable LastTypeVariable
Gets the last type variable created
Definition: TypeVariable.cs:81
override bool HasTypeVariables()
To know if the type expression has some type variables and requieres unification The default implemen...
override string ToString()
Abstract class that represents all different types.
Represents a generic type expression
Definition: TypeVariable.cs:36
override bool Equals(object obj)
override bool Remove(TypeVariable toRemove)
When loops are detected, it is necesary to suppress a new extra variable returned in the return type ...
override bool IsDynamic
Indicates if the type has been set as dynamic
string typeExpression
Represents the type by a debug string Note: WriteType expression is the longest recursive representat...
Representa a method type.
Definition: MethodType.cs:37
override object AcceptOperation(TypeSystemOperation op, object arg)
override bool Unify(TypeExpression te, SortOfUnification unification, IList< Pair< TypeExpression, TypeExpression >> previouslyUnified)
Check if the type can make a method operation.
override void UpdateEquivalenceClass(IDictionary< TypeVariable, TypeVariable > typeVariableMappings, IList< TypeExpression > previouslyUpdated)
Replaces the equivalence class of type variables substituting the old type variables for the new ones...
const int MAX_DEPTH_LEVEL_TYPE_EXPRESSION
In order to avoid stack overflow in the construction of typeexpression string (ToString), we set a maximum level of depth
TypeExpression Substitution
Gets the substitution; null if it does not exist
override TypeExpression CloneType(IDictionary< TypeVariable, TypeVariable > typeVariableMappings)
This method creates a new type variable. It these type variables where bounded to types or other type...
TypeExpression Freeze(IList< TypeExpression > evaluated)
override string BuildTypeExpressionString(int depthLevel)
The type expression following the following convention: variable={equivalenceclass}=substitution ...
EquivalenceClass EquivalenceClass
The equivalence class of the type variable (see the dragon book)
Definition: TypeVariable.cs:88
int Variable
Concrete value for the variable type
Definition: TypeVariable.cs:96
override TypeExpression Freeze()
WriteType variable may change its type&#39;s substitution (e.g., field type variables) This method return...