Vous êtes sur la page 1sur 77

O B J E C T O R I E N T E D

P R O G R A M M I N G
Course 5
Loredana STANCIU
loredana.stanciu@aut.upt.ro
Room B614
INTERFACES
A "contract" that spells out how a software
interacts with the environment
A reference type, similar to a class
Can contain only constants, method signatures,
and nested types
There are no method bodies
Cannot be instantiated can only be:
implemented by classes
extended by other interfaces
INTERFACES
public interface OperateCar {
// constant declarations, if any
// method signatures
int turn(Direction direction, double
radius, double startSpeed, double
endSpeed);
int changeLanes(Direction direction,
double startSpeed, double endSpeed);
......
// more method signatures
}
INTERFACES
To use an interface, you write a class that
implements the interface
Instantiable class provides a method body
for each of the methods declared in the
interface.
public class OperateBMW760i implements
OperateCar {
int changeLanes(Direction direction,
double startSpeed, double endSpeed){}
}
INTERFACES AS API
Application Programming Interface (API)
Very common in commercial software products.
A company sells a software package that
contains complex methods that another
company wants to use in its own software
product
INTERFACES AND MULTIPLE
INHERITANCE
Are not part of the class hierarchy, although
they work in combination with classes
The Java programming language does not
permit multiple inheritance, but interfaces
provide an alternative
A class can inherit from only one class but it
can implement more than one interface
objects can have multiple types:
of their own class
of all the interfaces that they implement
DEFINIG AN INTERFACE
public interface GroupedInterface extends
Interface1, Interface2, Interface3 {
// constant declarations
double E = 2.718282;
// method signatures
void doSomething (int i, double x);
int doSomethingElse(String s);
}
INTERFACES EXAMPLE
interface Reader{
public void read();}
interface Writer{
public void write();}
interface Professor extends Reader, Writer{
int max_mark=10;
int med_mark=5;
int min_mark=1;
public void evaluate();}
INTERFACES EXAMPLE
interface Diver {
int h=10;
public void diving();}
class Swimmer implements Diver {
static final int l=50;
public void swim() {
System.out.println("Swims " + l + "meters
");}
public void diving(){
System.out.println("Dives " + h +
"meters ");}
}
INTERFACES EXAMPLE
class SwimProfessor extends Swimmer
implements Professor{
public void read(){
System.out.println("Reads PRO Sport
");}
public void write(){
System.out.println("Never writes!");}
public void evaluate(){
System.out.println("Low. Gets " +
med_ mark);}
}
INTERFACES EXAMPLE
class JavaProfessor implements Professor {
public void read() {
System.out.println("Reads Thinking in
Java ");}
public void write() {
System.out.println("Writes Java
programs");}
public void evaluate() {
System.out.println("Excellent. Gets "
+ max_mark);}
}
INTERFACES EXAMPLE
INTERFACES EXAMPLE
public class TestInterface{
public static void main(String [] args){
SwimProfessor sp = new
SwimProfessor();
JavaProfessor jp = new
JavaProfessor();
sp.read(); sp.write();
sp.evaluate();
jp.read(); jp.write();
jp.evaluate();
sp.swim(); sp.dive(); //correct
jp.swim(); jp.dive(); //incorrect
}
USING AN INTERFACE AS A TYPE
Define a new interface defining a new
reference data type
If define a reference variable whose type is an
interface, any object assigned to it must be an
instance of a class that implements the
interface.
USING AN INTERFACE AS A TYPE
Professor sp = new SwimProfessor();
Professor jp = new JavaProfessor();
Use type casting to call methods that are not
defined in the interface
((SwimProfessor)sp).dive();
((SwimProfessor)sp).swim();
REWRITING INTERFACES
An initial version
public interface DoIt {
void doSomething(int i, double x);
int doSomethingElse(String s); }
Want to revise it
public interface DoIt {
void doSomething(int i, double x);
int doSomethingElse(String s);
boolean didItWork(int i, double x, String
s); }
REWRITING INTERFACES
All classes that implement the old DoIt
interface will break because they don't
implement the interface anymore
Try to anticipate all uses for your interface and
to specify it completely from the beginning
public interface DoItPlus extends DoIt {
boolean didItWork(int i, double x, String
s);
}
ABSTRACT CLASSES VERSUS
INTERFACES
All of the methods in an interface are
implicitly abstract
Abstract classes can contain fields that are
not static and final, and they can contain
implemented methods
If an abstract class contains only abstract
method declarations, it should be declared as
an interface
WHEN AN ABSTRACT CLASS
IMPLEMENTS AN INTERFACE?
If a class does not implement all of the
interface methods the class is declared to
be abstract
abstract class X implements Y {
// implements all but one method of Y
}
class XX extends X {
// implements the remaining method in Y
}
PROBLEM
Define an interface containing the following
methods:
void speedUp(double v, double t);
void breaks(double v, double t);
void constantMotion(double t);
void stop(double t);
and the constant MAX_SPEED=150 km/h.
Create a class to implement this interface
SOLUTION
Arguments
v [km/h]
t [s]
Computed values
a = dv/t [m/s^2]
d = d0 +v0t + a*t/2 [m]
SOLUTION
public interface CarOperation{
double MAX_SPEED=150;
void speedUp(double v, double t);
void breaks(double v, double t);
void constantMotion(double t);
void stop(double t);}
public interface Conversions{
double convertKmToM(double v);
double convertMToKm(double v);
double convertHToS(double v);
String convertToMinSec(double v);}
SOLUTION
public class Car implements CarOperation,
Conversions{
private double currentSpeed;
private double currentAcceleration;
private double distance;
private double time;
public Car(double cs, double t) {
currentSpeed = cs;
time = t;
distance =
(convertKmToM(currentSpeed)/convertHToS(1)) *
time;
currentAcceleration =
convertKmToM(currentSpeed)/(convertHToS(1) *
time);}
SOLUTION

public void speedUp(double v, double t){
time += t;
currentAcceleration =
convertKmToM(v)/(convertHToS(1)*t);
distance = distance +
(convertKmToM(currentSpeed)/convertHToS(1))*t
+ (convertKmToM(v)/convertHToS(1)*t)/2;
currentSpeed += v;}

SOLUTION

public void breaks(double v, double t){
time += t;
currentAcceleration = -
convertKmToM(v)/(convertHToS(1)*t);
distance = distance +
(convertKmToM(currentSpeed)/convertHToS(1))*t
- (convertKmToM(v)/convertHToS(1)*t)/2;
currentSpeed -= v;}

SOLUTION

public void constantMotion(double t){
time +=t;
currentAcceleration = 0;
distance = distance +
(convertKmToM(currentSpeed)/convertHToS(1))*t;}
public void stop(double t){
time += t;
currentAcceleration = -
(convertKmToM(currentSpeed)/convertHToS(1))/t;
distance = distance +
(convertKmToM(currentSpeed)/convertHToS(1))*t -
(convertKmToM(currentSpeed)/convertHToS(1))*t/2;
currentSpeed = 0;}

SOLUTION

public double convertKmToM(double v){
return v*1000;}
public double convertMToKm(double v){
return v/1000;}
public double convertHToS(double v){
return v*3600;}
public String convertToMinSec(double v){
return ""+((int)v/60)+" min " + (v%60) +" sec
";}

SOLUTION

public String toString(){
return String.format("The car has %n speed =
%6.2f km/h %n acceleration = %6.2f m/s^2 %n and
traveled a total of %6.2f km in %s
%n",currentSpeed, currentAcceleration,
convertMToKm(distance), convertToMinSec(time));
}
}
SOLUTION
public class Client{
public static void main (String [] arg){
CarOperation c = new Car(50,10);
System.out.println(c);
c.constantMotion(60);
System.out.println(c);
c.speedUp(20,30);
System.out.println(c);
c.breaks(10,10);
System.out.println(c);
c.constantMotion(600);
System.out.println(c);
c.stop(30);
System.out.println(c);}
}
GENERICS
In any software project, bugs are simply a fact
of life:
easier to detect: compile-time bugs
hard to detect: runtime bugs
Generics add stability to a code by making
more of the bugs detectable at compile time
GENERICS
A Simple Box Class operates on objects of
any type
public class Box {
private Object object;
public void add(Object object) {
this.object = object;}
public Object get() {
return object; }
}
GENERICS
To restrict the contained type to something
specific (like Integer) comments
public class BoxDemo1 {
public static void main(String[] args) {
// ONLY place Integer objects into this
box!
Box integerBox = new Box();
integerBox.add(new Integer(10));
Integer someInteger = (Integer)
integerBox.get();
System.out.println(someInteger);
}
}
GENERICS
public class BoxDemo2 {
public static void main(String[] args) {
// ONLY place Integer objects into this
box!
Box integerBox = new Box();
integerBox.add("10");
Integer someInteger =
(Integer)integerBox.get();
System.out.println(someInteger);
}
}
GENERICS
Exception in thread "main
java.lang.ClassCastException:
java.lang.String cannot be cast to
java.lang.Integer at
BoxDemo2.main(BoxDemo2.java:6)
If the Box class had been designed with
generics, this mistake would have been
caught by the compiler, instead of crashing
the application at runtime
GENERIC TYPES
First create a generic type declaration
public class Box<T>;
Introduces one type variable, named T, that can
be used anywhere inside the class
any class type
any interface type
can't be any of the primitive data types
T is a formal type parameter of the Box class
GENERIC TYPES
// Generic version of the Box class.
public class Box<T> {
private T t; // T stands for "Type
public void add(T t) {
this.t = t;
}
public T get() {
return t;
}
}
GENERIC TYPES
To reference the generic class must perform a
generic type invocation (passing a type
argument)
Box<Integer> integerBox;
An invocation of a generic type a
parameterized type.
integerBox = new Box<Integer>();
Box<Integer> integerBox = new Box<Integer>();
GENERIC TYPES
public class BoxDemo3 {
public static void main(String[] args) {
Box<Integer> integerBox = new
Box<Integer>();
integerBox.add(new Integer(10));
Integer someInteger = integerBox.get();
// no cast!
System.out.println(someInteger);
}
}
GENERIC TYPES
public class BoxDemo3 {
public static void main(String[] args) {
Box<Integer> integerBox = new
Box<Integer>();
integerBox.add(new Integer("10");
Integer someInteger = integerBox.get();
// no cast!
System.out.println(someInteger);
}
}
GENERIC TYPES
BoxDemo3.java:5: add(java.lang.Integer) in
Box<java.lang.Integer>
cannot be applied to (java.lang.String)
integerBox.add("10");
^
1 error
GENERIC METHODS AND
CONSTRUCTORS
Generic methods and generic constructors
public class Box<T> {
private T t;
public void add(T t) {
this.t = t; }
public T get() {
return t; }
public <U> void inspect(U u){
System.out.println("T: " +
t.getClass().getName());
System.out.println("U: " +
u.getClass().getName()); }
GENERIC METHODS AND
CONSTRUCTORS
Generic methods and generic constructors
public static void main(String[] args) {
Box<Integer> integerBox = new
Box<Integer>();
integerBox.add(new Integer(10));
integerBox.inspect("some text"); } }
The output from this program is:
T: java.lang.Integer
U:java.lang.String
BOUNDED TYPE PARAMETERS
Restrict the kinds of types that are allowed to be
passed to a type parameter
public class Box<T> {

public <U extends Number> void inspect(U u){
System.out.println("T:" + t.getClass().getName());
System.out.println("U:" + u.getClass().getName());
}
BOUNDED TYPE PARAMETERS
public static void main(String[] args) {
Box<Integer> integerBox = new Box<Integer>();
integerBox.add(new Integer(10));
integerBox.inspect("some text");
// error: this is still String!
} }
Box.java:21: <U>inspect(U) in
Box<java.lang.Integer> cannot be applied to
(java.lang.String)
integerBox.inspect("10");
^
SUBTYPING
Object someObject = new Object();
Integer someInteger = new Integer(10);
someObject = someInteger; // OK
"is a" relationship
public void someMethod(Number n){}
someMethod(new Integer(10)); // OK
someMethod(new Double(10.1)); // OK
SUBTYPING
Can assign an object of one type to an object of another
type if the types are compatible
Box<Number> box = new Box<Number>();
box.add(new Integer(10)); // OK
box.add(new Double(10.1)); // OK
public void boxTest(Box<Number> n){ //
method body omitted }
What type of argument does it accept?
WILDCARDS
An unknown type is represented by the
wildcard character "?".
Cage<? extends Animal> someCage = ...;
an unknown type that is a subtype of
Animal, possibly Animal itself
A bounded wildcard, where Animal forms the
upper bound of the expected type
It's also possible to specify a lower bound
<? super Animal>
TYPE ERASURE
A technique used by the compiler to
translate the generic types;
Box<String> is translated to type Box,
which is called the raw type a generic
class or interface name without any type
arguments
Cannot find out what type of Object a
generic class is using at runtime
TYPE ERASURE
public class MyClass<E> {
public static void myMethod(Object item) {
if (item instanceof E) {
//Compiler error ... }
E item2 = new E(); //Compiler error
E[ ] iArray = new E[10]; //Compiler
error
E obj = (E)new Object(); //Unchecked
cast warning
}
}
PROBLEM
Change the implementation of class
Polygon from course 4 to define its field
as an array of any of Numeric types.
Also, define the class Square which
inherits Polygon to have Integer
sides.
SOLUTION
class Polygon<T extends Number> {
private T[ ] sides;
private int i;
public Polygon(T[] n) {
sides = n;
i=0;}
public void add(T val) {
sides[i++]=val;}
public T getVal(int poz){
return sides[poz];}
}
SOLUTION
public class Square extends Polygon<Integer>{
public Square(Integer s){
super(new Integer[4]);
for(int i=0;i<4;i++)
add(s);}
public double perimeter(){
double sum = 4*getVal(0).doubleValue();
return sum;}
public double area(){
double sum =
Math.pow(getVal(0).doubleValue(),2);
return sum;}
}
SOLUTION
import java.io.*;
public class Client{
public static void main(String []arg) throws
IOException{
BufferedReader in = new BufferedReader(new
InputStreamReader (System.in));
System.out.println("Give the square's side
length");
Square s = new Square
(Integer.parseInt(in.readLine()));
System.out.printf("The square has the
perimeter = %6.2f and area = %6.2f %n",
s.perimeter(), s.area());}
}
PACKAGES
A grouping of related types providing access
protection and name space management
Types refers to classes, interfaces,
enumerations, and annotation types
The types part of the Java platform are
members of various packages that bundle
classes by function:
fundamental classes in java.lang
classes for reading and writing in java.io.
CREATING AND USING PACKAGES
//in the Draggable.java file
public interface Draggable { . . . }
//in the Graphic.java file
public abstract class Graphic { . . . }
//in the Rectangle.java file
public class Rectangle extends Graphic
implements Draggable { . . . }
. . .
CREATING AND USING PACKAGES
Reasons to bundle the classes and the
interface in a package:
can easily determine that these types are
related
know where to find types that can provide
graphics-related functions
avoid name conflict because the package
creates a new namespace
CREATING AND USING PACKAGES
You can allow types within the package to have
unrestricted access to one another yet still
restrict access for types outside the package.
protected int p;
CREATING A PACKAGE
Choose a name for the package and put a
package statement with that name at the top
of every source file that contains the types
The package statement (for example, package
graphics;) must be the first line in the
source file
Can be only one package statement in each
source file, and it applies to all types in the file
CREATING A PACKAGE
Important
If you put multiple types in a single source file,
only one can be public, and it must have the
same name as the source file
All the top-level, non-public types will be
package private are visible only in the
package, but not outside it
CREATING A PACKAGE
//in the Draggable.java file
package graphics;
public interface Draggable { . . . }
//in the Graphic.java file
package graphics;
public abstract class Graphic { . . . }
//in the Rectangle.java file
package graphics;
public class Rectangle extends Graphic
implements Draggable { . . . }
. . .
CREATING A PACKAGE
If you do not use a package statement,
your type ends up in an unnamed
package
Only for small or temporary applications
or when you are just beginning the
development process
Classes and interfaces belong in named
packages
NAMING A PACKAGE
The compiler allows many classes to have
the same name if they are in different
packages
The fully qualified name of each
Rectangle class includes the package
name
graphics.Rectangle (defined by
user)
java.awt.Rectangle (predefined)
NAMING CONVENTIONS
Package names are written in all
lowercase to avoid conflict with the
names of classes or interfaces.
Name collisions that occur within a single
company need to be handled by
convention within that company.
Packages in the Java language itself
begin with java. or javax.
USING PACKAGE MEMBERS
The types that comprise a package the
package members.
To use a public package member from outside
its package:
Refer to the member by its fully qualified name
Import the package member
Import the member's entire package
REFERRING TO A PACKAGE MEMBER BY
ITS QUALIFIED NAME
Can use a package member's simple name if
the code just writing is in the same package as
that member or if that member has been
imported
If trying to use a member from a different
package and that package has not been
imported, must use the member's fully qualified
name:
graphics.Rectangle
REFERRING TO A PACKAGE MEMBER BY
ITS QUALIFIED NAME
To create an instance of graphics.Rectangle:
graphics.Rectangle myRectangle = new
graphics.Rectangle();
Qualified names are all right for infrequent
use, but make the code difficult to read in
repeatedly used.
IMPORTING A PACKAGE MEMBER
Put an import statement at the beginning of
the file before any type definitions but after
the package statement, if there is one
import graphics.Rectangle;
To create an instance
Rectangle myRectangle = new
Rectangle();
IMPORTING AN ENTIRE PACKAGE
To import all the types contained in a
particular package, use the import statement
with the asterisk (*) wildcard character.
import graphics.*;
can refer to any class or interface in the
graphics package by its simple name.
Circle myCircle = new Circle();
Rectangle myRectangle = new
Rectangle();
IMPORTING PACKAGES
The Java compiler automatically imports three
entire packages for each source file:
(1) the package with no name
(2) the java.lang package
(3) the current package (the package for
the current file)
APPARENT HIERARCHIES OF PACKAGES
Packages appear to be hierarchical, but they
are not.
Packages in Java API
java.awt
java.awt.color
java.awt.font
Prefix java.awt (the Java Abstract Window
Toolkit) used for a number of related
packages to make the relationship evident,
but not to show inclusion.
APPARENT HIERARCHIES OF PACKAGES
import java.awt.*; imports all of
the types in the java.awt package, but it does
not import java.awt.xxxx packages.
import java.awt.*;
import java.awt.color.*;
THE STATIC IMPORT STATEMENT
Gives a way to import the constants and static
methods
java.lang.Math
public static final double PI
3.141592653589793
public static double cos(double a)
double r = Math.cos(Math.PI * theta);
THE STATIC IMPORT STATEMENT
import static java.lang.Math.PI;
or
import static java.lang.Math.*;
double r = cos(PI * theta);
MANAGING SOURCE AND CLASS FILES
Put the source code for a class, interface,
enumeration, in a text file whose name is the
simple name of the type and whose extension is
.java
// in the Rectangle.java file
package graphics;
public class Rectangle() { . . . }
MANAGING SOURCE AND CLASS FILES
Put the source file in a directory whose name
reflects the name of the package to which the
type belongs:
...../graphics/Rectangle.java
REFERENCES
The Java Tutorials. Interfaces.
http://java.sun.com/docs/books/tutorial/java/IandI
/createinterface.html
The Java Tutorials. Generics.
http://java.sun.com/docs/books/tutorial/java/gene
rics/index.html
Gilad Bracha, Generics,
http://java.sun.com/docs/books/tutorial/extra/gene
rics/index.html
REFERENCES
The Java Tutorials. Packages.
http://java.sun.com/docs/books/tutorial/java/pack
age/index.html

Vous aimerez peut-être aussi