Herhaling Objectgeorïenteerd werken is gebaseerd op de objecten die door het systeem gemanipuleerd worden. De basisbouwsteen is het object; een geïntegreerde eenheid van data en operaties werkend op deze data. Objecten bieden de opgeslagen data bescherming, laten zich makkelijk combineren tot softwaresystemen en zijn goed in isolatie te begrijpen. Objecten zijn gegroepeerd in klassen. Java is een voorbeeld van een pure objectgeoriënteerde programmeertaal. Overerving (inheritance) Eén van de belangrijkste eigenschappen van objectgeoriënteerde talen is de mogelijkheid tot overerving. Hierbij is het mogelijk nieuwe klassen te definiëren als uitbreiding op een bestaande klasse. Voorbeeld class Employee { protected String name; protected int phone; public Employee(String name, int phone) { this.name = name; this.phone = phone; } @Override public String toString() { return name + " phone: " + phone; } } Overerving (inheritance) class Manager extends Employee { private List<Employee> employees; public Manager(String name, int phone) { super(name,phone); employees = new ArrayList<>(); } public void addEmployee(Employee employee) { employees.add(employee); } public List<Employee> getEmployees() { return employees; } @Override public String toString() { String result = name + " phone: " + phone + "\nEmployees:\n"; for (Employee employee : employees) { result += " " + employee + "\n"; } return result; } } Manager erft van Employee en is dus een uitbreiding van Employee. Overerving (inheritance) Het voordeel is dat we de code van Employee niet nog eens hoeven over te nemen. Dit is vooral belangrijk bij onderhoud van software. Bij overname van code zouden er bij wijzigingen in Employee op twee plaatsen aanpassingen moeten plaatsvinden. Nu hoeft dat maar op één plaats. Terminologie Manager is een subklasse van Employee Employee is een superklasse van Manager Manager heet ook wel een subtype van Employee Anders gezegd: iedere Manager is een Employee, maar omgekeerd niet. Voor overerving geldt, net zoals voor klassen en objecten, dat dit begrip overeenkomt met onze intuitie. In het dagelijks leven brengen we vergelijkbare hierarchieën aan: dieren <− zoogdieren <− apen <− gorilla’s <− vogels <− mussen Polymorfisme en dynamische typering Aan een variabele van een superklasse mag een object van een subklasse worden toegekend. Manager kees = new Manager("Kees",890); Employee p = kees; Een restrictie hierbij is dat door de sterke typering van Java de methoden van Manager niet gebruikt mogen worden voor p. kees.getEmployees(); p.getEmployees(); // mag wel // mag niet Wil je dit wel kunnen doen, dan moet er een zgn. typecast plaatsvinden. ((Manager) (p)).getEmployees();// mag wel,vermijden Het kan echter nog mooier! Het is mogelijk de keuze van een methode af te laten hangen van het type van het object zelf (en niet van het type van de variabele). Dynamische typering Zowel Employee als Manager bevat methode toString. Employee piet = new Employee("Piet",123); Employee wim = new Employee("Wim",456); Manager kees = new Manager("Kees",890); Employee p = kees; List<Employee> employees = new ArrayList<>(); kees.addEmployee(piet); kees.addEmployee(wim); employees.add(piet); employees.add(kees); for (Employee employee : employees) { System.out.println(employee.toString()); In de for lus wordt zowel de Employee als Manager versie van toString aangeroepen afh van het dynamische type Overerving in Java In Java hebben alle klassen een gemeenschappelijke superklasse Object. Iedere klasse erft dus direkt of indirect van deze klasse. De volgende methoden maken onderdeel uit van Object: bool equals(Object obj); // gelijkheid van objecten String getClass(); // klassenaam als string String toString(); // stringrepresentatie van object equals en toString worden vaak overschreven. In de standaarbibliotheek wordt vaak inheritance toegepast. voorbeeld De Frameklasse dient alleen maar om van te erven. Deze klasse zorgt voor de basisfunctionaliteit van een window: het tekenen, het afvangen van events, windowmanagement. Alleen de applicatiespecifieke functionaliteit moet nog worden toegevoegd. Soorten overerving Java heeft twee syntaktische constructies voor overerving: extends: wordt het meest gebruikt implements: wordt gebruikt om een implementatie voor een interface te geven Interfaces worden gebruikt om functionaliteit af te dwingen Een klasse kan een implementatie van meerdere interfaces zijn en tegelijkertijd ook nog een extentie van weer een andere klasse. Voorbeeld Interface public interface Printable { public String print(); } class Abc implements Printable { @Override public String print() { return "Abc"; } Voordelen van overerving hergebruik van software toegenomen betrouwbaarheid van software code sharing consistente interfaces software componenten ondersteuning RAD en rapid prototyping ondersteuning polymorfisme ondersteuning design patterns en frameworks: bv. awt information hiding (bij erven alleen kennis van interface) Abstracte klassen • abstracte klassen zijn klassen waarvan nooit rechtstreeks een object wordt gecreëerd • van abstracte klassen wordt alleen gebruik gemaakt door overerving • een klasse is abstract als hij een abstracte methode bevat • interface is een voorbeeld van een abstracte klasse In het tekenprogramma zullen we voorbeelden van abstracte klassen zien