32
UE 2I002 (ex LI230) : éléments de programmation par objets avec Java TD8 - Héritage et liaison dynamique Juliana Silva Bernardes [email protected] http://www.lcqb.upmc.fr/julianab/teaching/JAVA/

UE 2I002 (ex LI230) : éléments de programmation par objets

  • Upload
    others

  • View
    1

  • Download
    0

Embed Size (px)

Citation preview

Page 1: UE 2I002 (ex LI230) : éléments de programmation par objets

UE 2I002 (ex LI230) : éléments de programmation par objets avec Java TD8 - Héritage et liaison dynamique

!!!

Juliana Silva [email protected]

http://www.lcqb.upmc.fr/julianab/teaching/JAVA/

Page 2: UE 2I002 (ex LI230) : éléments de programmation par objets

2

‣Transtypage d’objet (Cast)

‣instanceof

‣Méthode equals()

‣Liaison dynamique

‣Contexte de méthode

Sumary

Page 3: UE 2I002 (ex LI230) : éléments de programmation par objets

3

Transtypage des types primitifs

‣ Transtypage implicite‣On peut affecter à un champ ou une variable d'un type une expression de type

moins élevé dans la hiérarchie des types.

inta=100;floatb=a;

charshortintfloatdoublelong

Page 4: UE 2I002 (ex LI230) : éléments de programmation par objets

4

floata=100;intb=a;

‣ Transtypage explicite‣Mais nous pouvons pas faire le contraire, sans une Transtypage explicite

TestCast.java:7: error: incompatible types: possible lossy conversion from float to int int b = a; ^ 1 error

Transtypage des types primitifs

charshortintfloatdoublelong

Page 5: UE 2I002 (ex LI230) : éléments de programmation par objets

5

floata=100; //intb=a; intb=(int)a;

‣ Transtypage explicite

Transtypage des types primitifs

charshortintfloatdoublelong

Page 6: UE 2I002 (ex LI230) : éléments de programmation par objets

6

floatb=100.87f;intb=(int)a;System.out.println(b);

‣ Transtypage explicite‣Mais attention on pert en precision

Transtypage des types primitifs

charshortintfloatdoublelong

100Dans le terminal

Page 7: UE 2I002 (ex LI230) : éléments de programmation par objets

7

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intx=2;intz=3;publicintgetX(){returnx;}publicintgetZ(){returnz;}}

‣ Transtypage implicite des objets

publicclassTestCast{ publicstaticvoidmain(String[]args){ Aa=newA(); Bb=newB(); a=b; } } Le plus spécifique peut être

attribuer au plus générale

AB

Heritage

Page 8: UE 2I002 (ex LI230) : éléments de programmation par objets

8

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intx=2;intz=3;publicintgetX(){returnx;}publicintgetZ(){returnz;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Aa=newA(); Bb=newB(); b=a; } }

javac TestCast.java TestCast.java:5: error: incompatible types: A cannot be converted to B b = a; ^ 1 error Juliana

Le plus générale ne peut pas être attribuer au plus spécifique

‣ Transtypage implicite des objets

AB

Page 9: UE 2I002 (ex LI230) : éléments de programmation par objets

9

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intx=2;intz=3;publicintgetX(){returnx;}publicintgetZ(){returnz;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Aa=newA(); Ab=newB(); b=a; System.out.println(b.getX()); } }

$ javac *.java$ java TestCast$0

‣ Transtypage implicite des objets

AB

La methode getX() existe dans la class A, pas d’error de compilation

Page 10: UE 2I002 (ex LI230) : éléments de programmation par objets

10

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Aa=newA(); Ab=newB(); b=a; System.out.println(b.getY()); } }

$ javac *.java$ java TestCast

$ 1

‣ Transtypage implicite des objets

AB

La methode getY() existe dans la class A, pas d’error de compilation

Page 11: UE 2I002 (ex LI230) : éléments de programmation par objets

11

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Aa=newA(); Ab=newB(); b=a; System.out.println(b.getZ()); } }javac TestCast.java TestCast.java:6: error: cannot find symbol System.out.println(b.getZ()); ^ symbol: method getZ() location: variable b of type A 1 error

‣ Transtypage implicite des objets

La methode getZ() n'existe pas dans la class A, d’error de compilation

AB

Page 12: UE 2I002 (ex LI230) : éléments de programmation par objets

12

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsB{inte=2;publicintgetE(){returne;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Ac=newC(); Bb=c; System.out.println(b.getX()); } }javac TestCast.java TestCast.java:4: error: incompatible types: A cannot be converted to B B b = c; ^ 1 error !

‣ Transtypage implicite des objets

ABC

ABC

Page 13: UE 2I002 (ex LI230) : éléments de programmation par objets

13

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsB{inte=2;publicintgetE(){returne;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Ac=newC(); Bb=(B)c; System.out.print(b.getX()); System.out.println(b.getZ()); } }

‣ Transtypage explicite des objets

$ javac TestCast.java$ java TestCast$ 0 4

ABC

Page 14: UE 2I002 (ex LI230) : éléments de programmation par objets

14

Transtypage d’objet (Cast)

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsB{inte=2;publicintgetE(){returne;}}

publicclassTestCast{ publicstaticvoidmain(String[]args){ Ac=newC(); Bb=(B)c; Cc2=(C)c; System.out.println(b.getX()); System.out.println(c2.getE()); } }

$ javac *.java$ java TestCast$ 0 2

‣ Transtypage explicite des objets

ABC

Page 15: UE 2I002 (ex LI230) : éléments de programmation par objets

15

Instanceof

Page 16: UE 2I002 (ex LI230) : éléments de programmation par objets

16

Instanceof

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=2;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ A[]tab=newA[10]; for(inti=0;i<tab.length;i++){ if(Math.random()<0.3){ tab[i]=newB(); }else{ tab[i]=newC(); } } } }

‣On veut créer un tableau pour mettre 30% d'objets du type B et 70% du type C

Page 17: UE 2I002 (ex LI230) : éléments de programmation par objets

17

Instanceof

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ A[]tab=newA[10]; for(inti=0;i<tab.length;i++){ if(Math.random()<0.3) tab[i]=newB(); else tab[i]=newC(); }! for(inti=0;i<tab.length;i++){ Aa=tab[i]; if(ainstanceofB) System.out.println(a.getW()); elseif(ainstanceofC) System.out.println(a.getE()); } } }

‣ Pour les objets du type B, on va imprimer la sortie de la méthode getW(), pour les objets du type C, on va imprimer la sortie de la méthode getE()

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

$ javac *.java TestCast.java:15: error: cannot find symbol System.out.println(a.getW()); ^ symbol: method getW() location: variable a of type A TestCast.java:17: error: cannot find symbol System.out.println(a.getE()); ^ symbol: method getE() location: variable a of type A 2 errors

Page 18: UE 2I002 (ex LI230) : éléments de programmation par objets

18

Instanceof

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ A[]tab=newA[10]; for(inti=0;i<tab.length;i++){ if(Math.random()<0.3) tab[i]=newB(); else tab[i]=newC(); } for(inti=0;i<tab.length;i++){ Aa=tab[i]; if(ainstanceofB){ Bb=(B)a; System.out.println(b.getW()); } elseif(ainstanceofC){ Cc=(C)a; System.out.println(c.getE()); } } }}

‣ Pour les objets du type B, on va imprimer la sortie de la méthode getW(), pour les objets du type C, on va imprimer la sortie de la méthode getE()

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

Page 19: UE 2I002 (ex LI230) : éléments de programmation par objets

19

Instanceof

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ A[]tab=newA[10]; for(inti=0;i<tab.length;i++){ if(Math.random()<0.3) tab[i]=newB(); else tab[i]=newC(); }! for(inti=0;i<tab.length;i++){ Aa=tab[i]; if(ainstanceofB) System.out.println(((B)a).getW()); elseif(ainstanceofC) System.out.println(((C)a).getE()); } }

‣ Pour les objets du type B, on va imprimer la sortie de la méthode getW(), pour les objets du type C, on va imprimer la sortie de la méthode getE()

Page 20: UE 2I002 (ex LI230) : éléments de programmation par objets

20

Méthode equals()

Page 21: UE 2I002 (ex LI230) : éléments de programmation par objets

21

Méthode equals()

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ Cc1=newC(); System.out.print(c1.getE()); Cc2=newC(); System.out.println(c2.getE()); if(c1==c2) System.out.println(“égaux"); else System.out.println(“différents”); }}

‣Comment comparer deux objets?

$ javac *.java$ java TestCast$ 2 2$ différents

Page 22: UE 2I002 (ex LI230) : éléments de programmation par objets

22

Méthode equals()

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}}

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ Cc1=newC(); System.out.print(c1.getE()); Cc2=newC(); System.out.println(c2.getE()); if(c1.equals(c2)) System.out.println(“égaux"); else System.out.println(“différents”); }}

‣Comment comparer deux objets?

$ javac *.java$ java TestCast$ 2 2$ différents

La méthode equals de la class object verifier si les pointeur des objets sont égaux.

Page 23: UE 2I002 (ex LI230) : éléments de programmation par objets

23

Méthode equals()

publicclassA{privateintx=0;privateinty=1;publicintgetX(){returnx;}publicintgetY(){returny;}}publicclassBextendsA{intw=5;intz=3;publicintgetW(){returnw;}publicintgetZ(){returnz;}}publicclassCextendsA{inte=2;publicintgetE(){returne;}publicbooleanequals(Cc){ return(e==c.e);}}

publicclassTestInstanceOf{ publicstaticvoidmain(String[]args){ Cc1=newC(); System.out.print(c1.getE()); Cc2=newC(); System.out.println(c2.getE()); if(c1.equals(c2)) System.out.println(“égaux"); else System.out.println(“différents”); }}

‣Comment comparer deux objets?

$ javac *.java$ java TestCast$ 2 2$ égaux

On doit redefinir la method equals.

Page 24: UE 2I002 (ex LI230) : éléments de programmation par objets

24

Liaison dynamique

Page 25: UE 2I002 (ex LI230) : éléments de programmation par objets

25

Liaison dynamique

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); }}

$ javac *.java$ java QuelleMethode$ niveau a

La variable a référence un objet de type A ; de toute évidence, la méthode faire utilisée à l'exécution est la méthode faire de la classe A

Page 26: UE 2I002 (ex LI230) : éléments de programmation par objets

26

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); a=newB(); a.faire();}}

$ javac *.java

Le compilateur regarde le type de la variable a, il s'agit de A, et déciderait donc qu'il s'agit de la méthode faire de la classe A, on obtiendrai niveau a.

Liaison dynamique

Page 27: UE 2I002 (ex LI230) : éléments de programmation par objets

27

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); a=newB(); a.faire();}}

$ javac *.java

Le compilateur ne peut pas savoir quel objet sera référencé par la variable a à l’exécution.Le compilateur ne remonte jamais dans l'historique des instructions

Liaison dynamique

Page 28: UE 2I002 (ex LI230) : éléments de programmation par objets

28

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); a=newB(); a.faire();}}

$ javac *.java

Le compilateur se limite à vérifier que la classe A possède une méthode faire ayant des paramètres correspondant aux paramètres de l'appel

Liaison dynamique

Page 29: UE 2I002 (ex LI230) : éléments de programmation par objets

29

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); a=newB(); a.faire();}}

La méthode faire à exécuter est décider à l’exécution. Le fait que la méthode soit déterminée à l'exécution s'exprime par le fait qu'il s'agit d'une liaison

dynamique

Liaison dynamique

$ javac *.java$ java QuelleMethode$ niveau a$ niveau b

Page 30: UE 2I002 (ex LI230) : éléments de programmation par objets

30

publicclassA{publicvoidfaire(){System.out.println("niveaua");}}!!publicclassBextendsA{publicvoidfaire(){ System.out.println("niveaub"); }}!publicclassCextendsB{}

publicclassQuelleMethode{publicstaticvoidmain(String[]argv){ Aa; a=newA(); a.faire(); a=newB(); a.faire(); a=newC(); a.faire();}}

L'objet référencé par a est de type C ; la classe C ne redéfinit pas la méthode faire ; la méthode utilisée est alors celle héritée de B.

Liaison dynamique

$ javac *.java$ java QuelleMethode$ niveau a$ niveau b$ niveau b

Page 31: UE 2I002 (ex LI230) : éléments de programmation par objets

31

Contexte de méthode

Page 32: UE 2I002 (ex LI230) : éléments de programmation par objets

32

Contexte de méthode

publicclassA{privateintx=0;publicintj(){returnx;}publicintk(){returnx;}}publicclassBextendsA{intx=5;publicintj(){returnx;}publicintu(){returnx;}}

publicclassTest{publicstaticvoidmain(String[]argv){ Aa=newA(); Bb=newB(); System.out.print(a.j()); !!!!!!!!!! }}

$ 0System.out.print(a.k()); $ 0System.out.print(b.j()); $ 5System.out.print(b.u()); $ 5a=bSystem.out.print(a.j()); $ 5System.out.print(a.k()); $ 0System.out.print(b.j()); $ 5System.out.print(b.u()); $ 5