Object Oriented Programming: DR O.Rifi
Object Oriented Programming: DR O.Rifi
Object Oriented Programming: DR O.Rifi
Programming
with
Java
Dr O.Rifi
Organized by S.Zaayter
Content
Contents
1 Compiled versus Interpreted Programming Languages 1
3 Static Methods 3
4 Arrays 4
• Compiled languages are converted directly into machine code (e.g. C language).
• Compiled languages need a "build" step - they need to be manually compiled first. You need to
"rebuild" the program every time you make a change.
• Interpreters will run through a program (written in an interpreted language) line by line and
execute each command (e.g. Prolog, PHP, Javascript).
• Java is a semi-interpreted language. You write a program in Java language, then you compile
it with Java compiler javac which converts your code into bytecode , finally you run your
program with java interpreter.
• An executable Java program consists of a method (function) main within a class structure.
public class MainClass {
• The instruction System.out.println("Hello World") would print the string (word) Hello World
to the console along with a new line. To stay on the same line we should use print instead of
println .
11
Primitive Data Types
• Integer: byte (1 byte), short (2 bytes), int (4 bytes), long (8 bytes) (e.g. 25l ou 25L).
• Floating point numbers: float (4 bytes) (e.g. 12.5f ou 12.5F), double (8 bytes).
• Note: Java Types are independent of machine architecture. It is not the case of C.
Control Structures
• Control Structures if-else , while , for , ... are used in the same way as in C.
public static void main(String[] args) {
int n = 2;
int p = 10;
int power = 1;
for (int i = 1; i <= p; i++) {
power *= n; // power = power * n;
}
System.out.printf("%d to the power %d = %d\n",n,p,power);
// or
System.out.println(n+" to the power "+p+" = "+power);
}
• Output
Give n: 2
Give p: 10
2 to the power 10 = 1024
22
Example: solving Quadratic Equations
public static void main(String[] args) {
double a, b, c;
System.out.print("Give coefficients a, b, c: ");
Scanner sc = new Scanner(System.in);
a = sc.nextDouble(); b=sc.nextDouble(); c=sc.nextDouble();
double delta;
delta = b * b - 4 * a * c;
if (delta < 0) {
System.out.println("No solution");
} else if (delta == 0) {
System.out.printf("Double root = %.2f%n", -b/(2*a));
} else {// delta > 0
double r = Math.sqrt(delta);
System.out.printf("x1 = %.2f, x2 = %.2f%n",
(-b+r)/(2*a), (-b-r)/(2*a));
}
}
3 Static Methods
Static Method (1)
33
int value = power(2,10);
System.out.printf("%d\n",value);
}
}
4 Arrays
Arrays(1)
• The latter code is just a variable declaration without any memory allocation.
• We can define an array and initialize its values in one instruction. Example
int[] tab = {4, 6, 9, 3, 5, 8, 2, 7, 1};
//the latter code is similar to:
int[] tab = new int[9];//tab has length 9
tab[0]=4;
tab[1]=6;
//...
Arrays(2)
44
Simple Sorting Method (2)
Output
run:
1 2 3 4 5 6 7 8 9
Output
run:
[1, 2, 3, 4, 5, 6, 7]
55
Content
Contents
1 Classes & Objects 1
2 Sending Messages 2
4 Encapsulation 4
Using a Class
We may use the latter definition of Point class in order to declare a variable of type Point :
public static void main(String[] arg) {
Point p;
}
in C:
void main(){
struct Point *p;
}
In the above two cases the variable p is just a future reference (pointer) to an object Point which is
not yet created (allocated a memory space).
Creating Objects
To create an Object in Java, we should use the new keyword.
public static void main(String[] arg) {
Point p;
// p is an instance of Point, Point() is a constructor call.
61
p = new Point();
}
in C:
void main(){
struct Point *p;
p = (struct Point*) malloc(sizeof(struct Point));
}
In C, we may define a variable of type Point without using a pointer so the object is immediately
created ( struct Point p; ). In Java, all variables (except those having primitive type) are only
references.
Output:
run:
q = [2, 3]
Object references
Once an object is created, it could be referenced by more than one variable.
public static void main(String[] arg) {
Point p = new Point();
p.x = 1;
p.y = 1;
// q refers the same object as p
Point q = p;
q.x = 2;
q.y = 2;
System.out.printf("p = [%d, %d]\n", p.x, p.y);
}
Output:
run:
p = [2, 2]
72
2 Sending Messages
Instance Methods (1)
To a class, we can add methods that define the behaviour of its instances (Objects).
public class Point {
int x;
int y;
double distance() {
return Math.sqrt(x * x + y * y);
}
}
Output:
run:
p = [3, 4]
Distance = 5.00
83
public static void main(String[] args) {
...
// this in move is a reference to p
p.move(3, 4);
...
}
4 Encapsulation
Encapsulation Principle: problem
Consider the following class Time :
public class Time {
int hour, min, sec;
}
It is supposed now that an object of type time should have values of its fields within a certain range
in order to be considered logically valid. That is, hour should be between 0 and 23, min and sec
should be between 0 and 59.
But from this class we can create logically invalid object:
public static void main(String[] args) {
Time t = new Time();
t.hour = 23;
t.min = 65; // min should have value >= 0 and < 60
t.sec = 45;
}
Now, all fields of class Time are inaccessible from outside the class. That is, the following code will
cause a compile error.
94
public static void main(String[] args) {
Time t = new Time();
t.hour = 23; // can’t access field hour from t because it is private
}
• When fields are private, the class implementer could change the class representation (fields
definition) and adapt the public methods without affecting the client user ( main method or any
other method in any other class).
• Suppose now that we want to change the representation of class Time from 3 int variables
(hour, min, sec) to one int variable secMed (seconds since midnight). (The class will become
more efficient in term of space complexity. That is, each object will occupy 4 bytes instead of
12 bytes in memory).
10
5
public class Time {
private int secMid;
11
6
Content
Contents
1 Constructors 1
2 Methods Overloading 3
4 Constants in Java 4
5 Objects Destruction 6
1 Constructors
Default Constructor
A class constructor is a particular method that has no return type and has a name which is exactly
the same as the class name. A class that does not have a constructor will be implicitly provided by a
default one. The following class
public class Point {
private int x, y;
}
public Point(){
}
}
Other Constructor
We may write a specific constructor with parameters allowing fields initialisation
public class Point {
private int x, y;
12
1
}
Many Constructors
We may have many constructors in the same class that differ by the type and/or by the number of
parameters
public class Point {
private int x, y;
public Point() {
this.x = this.y = 0;
}
public Point() {
this(0, 0);
}
Calling Constructors
We can use any of the three above constructors to create a Point object.
public static void main(String[] arg) {
Point p = new Point();
Point q = new Point(3, 4);
Point t = new Point(q);
System.out.println(t);
}
Output:
13
2
run:
[3, 4]
2 Methods Overloading
Methods Overloading
We may define many methods having the same name but different parameters in the same class.
public class Point {
private int x, y;
14
3
this.eps = eps;
}
• We define eps to be static , that is eps is now a class variable shared by all objects of that
class.
private double x, y;
private static double eps = 1.0e-5;
public static void setEps(double eps){
this.eps = eps;
}
• Class variables exist when the class is loaded into memory, before any object creation.
• Methods that manipulate class variables (static fields) should be defined as static.
• Static methods could be called from any object but also from the class itself ( Point.setEps(1.0e-2) ).
4 Constants in Java
Using the final modifier
We use the final modifier to make a variable (class or instance variable) constant. That is, once the
variable is given a value, that value could never be changed again.
15
4
public class Person {
private String name; private int age;
private final int yearOfBirth; // can’t initialise with a default value
Note: when we create an array ( int[] tab = new int[10] ), we can access its length using the
instruction tab.length . tab is an object of type array of integer and length is a public final
variable (field) which is set once for all when the array is created.
static{
// will be executed once the class is loaded.
double res = 3.0/4.0;
MAX_Y = MAX_X * res;
}
...
}
When a static variable is final, we should immediately initialise it or use a static block to define its
value.
A class is loaded when we create the first object or accessing a static variable or method.
• Math.PI : PI is a public static final variable in class Math representing the value of π.
• Math.E : E is a public static final variable in class Math representing the value of exp.
• System.out.println() :
– System is a class,
– out is a public static final variable in class System representing a PrintStream object
connected to the console,
– println() is an instance method in class PrintStream .
16
5
5 Objects Destruction
Garbage Collector(1)
• In C/C++, programmer is responsible for both creation and destruction of objects. Usually
programmer neglects destruction of useless objects. Due to this negligence, at certain point,
for creation of new objects, sufficient memory may not be available and entire program will
terminate abnormally causing Out Of Memory Errors.
• But in Java, the programmer need not to care for all those objects which are no longer in use.
Garbage collector destroys these objects.
Garbage Collector(2)
public static void main(String[] arg) {
Point p1 = new Point(1, 1);
Point p2 = new Point(2, 2);
p2 = null;
// point (2, 2) is no more referenced...
Method finalize
There is a particular method finalize that each class could define and that the garbage collector
will call on objects before removing them from memory.
public class Point {
private double x, y;
...
17
6
Content
Contents
1 Delegation 1
2 Inheritance (Specialisation/Generalisation) 3
1 Delegation
Delegation
• The client class C1 contains a field (attribute) of types C2 (e.g. Class Circle contains a field of
type Point representing its center instead of x & y).
public class Circle {
private int x, y;
private Point center;
private int radius;
Delegation Cont.
18
1
Delegation Cont.
public String toString() {
return String.format("[%.2f, %.2f], %.2f", x, y, radius);;
return center.toString() + ", " + radius;
}
}
Other examples:
public class Set {
private int[] tab = new int[100];
Aggregation vs Composition
• Delegation induces a relationship between two classes. It is a "has a" relationship. (A circle
"has a" Point).
• When an instance of a component (Point) can not be in relation with more than one aggregate
(Circle) and the component has a life cycle dependant of the aggregate, the relationship is said
to be a Composition. (In the above example of the class Circle, the center field is created
within the Circle constructor... When a Circle Object is destroyed the related Point object is
also destroyed.
• When the component has autonomous existence outside the aggregate, the relationship is said
to be an Aggregation. (Example follows).
Aggregation
public class Circle {
private Point center;
private int radius;
19
2
Aggregation Cont.
The output of the above main method:
run:
[1, 1], 5
[2, 2], 5
So you can see that when the object point has moved, the circle has moved also !
The object point has a life cycle that is independent from the object circle .
2 Inheritance (Specialisation/Generalisation)
Inheritance, Specialisation
• Suppose that we have an application which is in need of services that only some are already
defined by a given class (without necessarily having the code of that class). (E.g, we have the
class Point, but we need GraphicPoint: a point that could be displayed on a canvas)
• A GraphicPoint needs all attributes and operations (methods) that exist in Point but in addition,
it needs a field representing its color, and an operation that performs the drawing.
• Should we rewrite all the code of class Point to define GraphicPoint ? In fact, we can use the
existing class Point to define the class GraphicPoint by using inheritance.
• The relationship induced by inheritance is called "is a" relationship (GraphicPoint is a Point).
Specialisation Cont.
public class Point {
int x, y;
public Point() {
this(0, 0);
}
20
3
Specialisation Cont.
• A subclass inherits all attributes and methods from its superclass. It could define more attributes
and methods.
• A class can extend only one class (Inheritance in Java is not multiple).
• If attributes are privates, they are inherited but not accessible. (Use protected as modifier to
enable access.
• While designing classes, if the superclass exists before the subclasses, the process is called
Specialisation.
• If subclasses exist before the superclass, the process is called Generalisation (Abstraction).
• The inheritance relation is transitive. If C extends B and B extends A, then C inherits all
attributes and methods from B and A.
Methods Overriding
A subclass can override an inherited method. (The method, exactly same signature, is redefined in the
subclass.)
public class A {
A a = new A();
B b = new B();
Overriding vs Overloading
Do not confuse Overriding with Overloading.
public class A {
Overriding
21
4
public class B extends A {
C contains two methodX , one inherited with parameter int and the other defined in the class itself
with parameter double.
• By default, a class that does not extend another class, extends Object implicitly.
public class Point {...}
// same as
public class Point extends Object {...}
• The class Object contains many methods that are inherited by all other classes. Two of these
methods are of interest:
– String toString() method that we override in many classes. If not overridden, it re-
turns the class name followed by "@" followed by a certain hexadecimal text.
– boolean equals(Object o) which by by default returns true iff the parameter and the
current object are the same.
Constructors Reuse
Constructors are not inherited but could be reused in the definition of the subclass’ constructors.
public class Point {
protected int x, y;
public Point (int x, int y) {
this.x = x;
this.y = y;
}
}
22
5
super(x, y); // calls the constructor’s of the superclass.
// The call to super should be the first instruction.
this.color = color;
}
}
• If a constructor does not have an explicit call to super , the compiler will provide an implicit
call to it without parameters.
public class A {
private int i;
public A (int i) {
super(); // implicit call to the constructor of the class Object.
this.i = i;
}
}
• If a class does not not have a constructor defined explicitly, the compiler will provide a default
constructor calling the super constructor.
public class A {
public A () {
super();
}
}
• If class C extends B and B extends A, then a call to a constructor of class C chains up a call to a
constructor of B, then a call to a constructor of class A then a call to the constructor of the class
Object. Execution order of constructors is in reverse.
• A constructor of a subclass should call explicitly a constructor of its superclass if the superclass
does not have a default constructor.
public class A {
protected int i;
public A (int i) {
this.i = i;
}
}
• We can control the visibility of a class member (attribute or method) by using the following
modifiers:
– public accessible to any other class.
– private accessible only within the class itself.
– protected accessible to any subclass and to any class in the same package.
– package accessible to any class in the same package.
• Two levels of visibility for classes:
– public accessible to any other class.
– package accessible to any class in the same package.
23
6
Final classes and Methods
• When a class is final, it is forbidden to extend it. (Class String is final.) All methods are
implicitly final.
public final class A {
...
}
24
7
Content
Contents
1 Polymorphism 1
1 Polymorphism
Upcasting
• Class B that inherits from class A could be considered as a sub-type of the type defined by class
A.
• GraphicPoint is a Point .
• To a variable of type A, it is possible to assign a reference to an object of class B. ( Point p = new GraphicP
• Object is the root of any inheritance hierarchy, so all classes could be upcast to it. ( Object o = new Savin
Upcasting Cont.
• When an object is upcast to a super type, it is seen, by the compiler, as an object of that type,
so only methods defined in the superclass could be called from that object.
public class Point {
public void move(int dx, int dy) {...}
public double distance() {...}
public String toString(){
return String.format("[%d, %d]", x, y);
}
}
Dynamic Binding
• When a method is called, the compiler ensures that this method is defined in the class of the
static type.
25
1
• But, during execution, the method which is executed is the one that is overridden in the class of
the dynamic type (Dynamic Binding).
public static void main(String[] args) {
Point p = new GraphicPoint(...);
p.move(1, 1); // move in Point
p.distance(); // distance in Point
System.out.println(p.toString()); // toString in GraphicPoint
}
Polymorphism
• In OOP, Polymorphism is
– the fact that an object of a class could be manipulated as an object of another class (super-
class).
– the fact that the same operation (method) could behave differently according to the dy-
namic type of the caller object.
• Polymorphism is the third characteristic of any OOP language after Encapsulation and Inheri-
tance.
Polymorphism, Example
public class Account {
26
2
Downcasting
• When B inherits from A, we’ve seen that we can upcast an object of type B to a variable of type
A. ( A a = new B(); )
• Before downcast an object to a type, we’ve to ensure that this object is of that type.
if(a instanceof B){
B b = (B) a;
}
About equals
• Whenever objects of a class we’re defining need to be compared for equality with respect to the
values of their attributes, the method boolean equals(Object o) of the Object class should
be overridden.
public class Point {
private int x, y;
Point p = (Point) o;
return x == p.x && y == p.y;
}
}
double x, y
double radius
27
3
class Rectangle
double x, y
double width, height
class Triangle
double x, y
double x1, y1 // v1
double x2, y2 // v2
Remarks
• The class Shape has no useful meaning, that is no objects are needed from this class. It is there
just for upcasting and polymorphism.
• Class Shape is an abstract concept, so we can define it as abstract which forbids any object
creation.
• Methods in subclasses having same signature but different behaviors ( perimeter, area ) should
also be defined in class Shape so a Shape variable, whether it refers a Circle or a Rectangle could
call them.
• Such methods should be defined as abstract without any implementation.
Abstract Shape
• The class Shape should look like
public abstract class Shape {
protected double x, y;
28
4
• Each subclass of Shape should define (override) all abstract methods.
• Example of use
Shape sh = new Shape(...); //Error
Shape sh = new Rectangle(...);
sh.move(1, 1); // executes move in Shape
sh.perimeter(); // executes perimeter in Rectangle, but first the compiler ensures that
// perimeter is defined in Shape.
Java Interfaces
• Abstract classes are there to regroup subclasses belonging to the same family (having common
attributes and common behaviors (methods)).
• What if we want to regroup classes with respect to some behavior only? That is, classes with
no relation but having common behavior.
• E.g. objects of type Rational (number) and objects of type Time have common behavior: they
are all comparable.
• Suppose that we want to implement a sort(...) method that sorts an array of Rationals or an
array of Times, we have to find a structure to which we can upcast Rational and Time.
Interface Comparable
• Interface is like an abstract class, all methods declared are like abstract methods (they have no
implementation).
• The method compareTo should return a negative numbers if current object is less than o, 0 if
current is equal to o and a positive number otherwise.
• When a class implements an interface, it should implement all methods defined in that interface.
Object of this class could be upcast to a variable typed by that interface.
public class Time implements Comparable {
public int compareTo(Object o) {...}
}
29
5
tab[j] = aux;
}
}
}
}
sort(tab);
30
6