Presentation is loading. Please wait.

Presentation is loading. Please wait.

Type Checking  Legality checks  Operator determination  Overload resolution.

Similar presentations


Presentation on theme: "Type Checking  Legality checks  Operator determination  Overload resolution."— Presentation transcript:

1 Type Checking  Legality checks  Operator determination  Overload resolution

2 Type as a synthesized attribute Expr ::= Expr + Term if Etype (Expr 2 ) = Etype (Term) then Etype (Expr 1 ) := Etype (Expr 2 ); else Etype (Expr1) = Any_Type; Error (“incompatible types for +”, Expr 1 ); end if;  Sufficient for Pascal and C

3 Rules for operations on composite types Indexed_Component ::= Prefix ( Expr ) A_Typ := Etype (Prefix); Etype (Indexed_Component) := Any_Type; - - by default if not Is_Array_Type (A_Typ) then Error (“expect array type in indexed component”, Prefix); elsif Etype (Expr) /= Index_Type (A_Typ) then Error (“wrong index type”, Expr); else Etype (Indexed_Component) := Component_Type (A_Typ); end if;

4 Type expressions Built from: Primitive types: boolean, float, integer Type constructors: array, record, access, function Type_Expr ::= Prim_Type Type_Expr ::= Type_Name Type_Expr ::= array (Type_Expr) Type_Expr Pascal, Ada : index type is part of type expression Early Pascal : index bounds are part of type expression (bad idea) Type_Expr ::= record (…) Type_Expr ::= access Type_Expr Type checking is a set of rules to compute the type expressions of all expressions in the program

5 Product types and functions Type_Expr := Type_Expr * Type_Expr Intuitively, a pair of types Type_Expr := Type_Expr 1 -> Type_Expr 2 A function that takes an argument of type Type_Expr 1 and returns a value of type Type_Expr 2 function Distance (C1, C2 : Character) return Integer; Distance: character * character -> integer real merge (int[] a, int[]b); merge: array ( int ) * array ( int ) -> real

6 Type checking and type equivalence Type correctness can be stated in terms of equivalence of type expressions: int [ ] arr1; // arr2 : array ( int ) int [ ] arr2; // arr2 : array ( int ) … Arr1 = arr2; // ok in Java: type expressions are equivalent Usually the rule in languages where a declaration can contain an arbitrary type expression

7 Type checking and name equivalence Arr1 : array (1..10) of integer; Arr2 : array (1..10) of integer; … Arr1 := Arr2; // illegal in Ada: different anonymous types. -- same as: type anon1 is array (1..10) of integer; Arr1 : anon1; -- Arr1 : anon1 type anon2 is array (1..10) of integer; Arr2 : anon2: -- Arr2 : anon2 -- Arr1 and Arr2 are not equivalent. Language does not allow arbitrary (anonymous) type expressions in a declaration

8 Type expressions with cycles type t1 = record c: integer; p: pointer (t1); end record; type t2 = record c: integer; p: pointer (t2); end record; t1 and t2 are equivalent in Algol68 C approach: name of type is part of type expression, types are not equivalent: struct cell { int c; struct cell *next; /* struct cell is in type expression */ };

9 Type checking and coercions If language allows coercions, type depends on context, cannot be purely synthesized. For C++ boolean operators (Stroustrup C.6.3) If either operand is of type long double, the other is converted to long double Otherwise, if either operand is double, the other is converted to double Otherwise, if either is float, the other is converted to float Otherwise, integral promotions are performed on both: char, (un) signed_char, (unsigned) short int -> int bit-field -> int bool -> int Further complication: user-defined conversions.

10 Overload resolution If expression is overloaded, collect set of possible meanings sm. If context is overloaded, collect set of possible context types sc. Expression is legal in context if intersection of sc and sm is a singleton: | sc ∩ sm | = 1 C++: if multiple interpretations, select the one with smallest number of coercions Ada: if multiple interpretations, select predefined numeric operator over user-defined one

11 Overloaded context: procedure call procedure P (x : integer; y : float); procedure P (x : float; y : float); procedure P (x : boolean; z : integer); function F (x : integer) return boolean; function F (x : float) return integer; function F (x : integer) return float; function F (x : float) return boolean; … P (f (3.14), f (1)); -- P 1 (f 2 (3.14), f 3 (1));

12 Two-pass type resolution Bottom-up (analyze) : synthesize candidate types Top-down (resolve): propagate unique context type procedure analyze_indexed_component (N : Node_Id) is begin analyze prefix, collect set of interpretations Pre analyze index, collect set of interpretations Ind forall t in Pre loop if there is a compatible ix in Ind then add component_Type (t) to interpretations of N else remove t from Pre; end if; end loop; end;

13 Two-pass type resolution (2) procedure resolve_indexed_component (N : Node_Id; Typ : Entity_Id) is begin find unique interpretation of prefix whose component type is Typ resolve index using this interpretation end; General scheme: bottom-up: analyze descendants, synthesize local attribute top-down : disambiguate construct, propagate to descendants

14 Type variables and polymorphism In a language with list primitives (LISP, ML) what is the type expression that describes CAR or hd? Informally, given a list of components of any kind, CAR yields a value of that kind: Car : list_of_whatever -> whatever A type variable is universally quantified: the expression is valid for any instantiation of the variable. In ML notation: Head (hd) α list -> α Tail (tl) α list -> α list Constructor (::) : α * α list -> α list

15 Polymorphic functions fun len lis = if lis = null then 0 else 1 + len (tl lis) Len : α list -> int fun map (f lis) = if L = null then null else f (hd lis) :: map (f (tl lis)) Map: (α ->β) * α list -> β list Map applies a function to each element of a list. The result type of the function is not necessarily equal to the element type of the list.

16 The limits of type inference Overloading must be handled specially Self-application is not typable: 1 + g (g) g is a function: g: α -> β g applied to itself yields an integer: β = int α = α -> β : circular definition (not unifiable)


Download ppt "Type Checking  Legality checks  Operator determination  Overload resolution."

Similar presentations


Ads by Google