Skip to content

Commit

Permalink
Add Java OOP (part I) code snippets
Browse files Browse the repository at this point in the history
  • Loading branch information
100yo committed Oct 18, 2024
1 parent ce0fa68 commit 6abe0f5
Show file tree
Hide file tree
Showing 19 changed files with 373 additions and 0 deletions.
1 change: 1 addition & 0 deletions 02-oop-in-java-i/snippets/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
# OOP in Java (part I) / Code snippets
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package bg.sofia.uni.fmi.mjt.adorable;

public abstract class AbstractCoolPerson implements Adorable {

// We are not required to implement the methods in an abstract class.

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package bg.sofia.uni.fmi.mjt.adorable;

interface Adorable extends Likeable, Lovable {

// This interface inherits both like() and love() methods and does not define new methods.
// Any class that will implement it, is required to implement both like() and love(), or declare itself as abstract.

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package bg.sofia.uni.fmi.mjt.adorable;

public class CoolPerson implements Adorable {
// If we do not implement all Adorable methods, we will get a compile-time error:
// "CoolPerson is not abstract and does not override abstract method like() in Likeable"

@Override
public void like() {
System.out.println("I am liked!");
}

@Override
public void love() {
System.out.println("I am loved!");
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package bg.sofia.uni.fmi.mjt.adorable;

interface Likeable {

void like();

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package bg.sofia.uni.fmi.mjt.adorable;

interface Lovable {

void love();

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
package bg.sofia.uni.fmi.mjt.instanceoff;

class Shape {
void draw() {
System.out.println("Drawing a shape");
}
}

class Circle extends Shape {
@Override
void draw() {
System.out.println("Drawing a circle");
}
}

class Rectangle extends Shape {
@Override
void draw() {
System.out.println("Drawing a rectangle");
}
}

public class InstanceOfExample {

public static void main(String[] args) {
Shape[] shapes = new Shape[]{
new Circle(),
new Rectangle(),
new Circle(),
new Rectangle(),
};

// old-school way:
for (Shape shape : shapes) {
if (shape instanceof Circle) {
System.out.println("Circle detected:");
Circle circle = (Circle) shape; // Cast to Circle
circle.draw();
} else if (shape instanceof Rectangle) {
System.out.println("Rectangle detected:");
Rectangle rectangle = (Rectangle) shape; // Cast to Rectangle
rectangle.draw();
} else {
System.out.println("Unknown shape detected.");
shape.draw();
}
}

// equivalent with enhanced switch
for (Shape shape : shapes) {
switch (shape) {
case Circle c -> c.draw();
case Rectangle r -> r.draw();
default -> System.out.println("Unexpected value: " + shape);
}
}
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
package bg.sofia.uni.fmi.mjt.lockable;

public class DefaultInterfaceExamples {

public static void main(String... args) {

Door door = new Door();
Lockable anotherDoor = new Door();
Lockable safe = new Safe();
anotherDoor.lock(); // Door locked.
System.out.println(safe.isLocked()); // false
System.out.println(door.isLocked()); // true

Object obj = new Safe();
Lockable lockable = Lockable.getInstance(true);

// classic instanceof: explicit cast is needed in the if body
if (obj instanceof Lockable) {
((Lockable) obj).lock(); // Safe locked.
}

// New in Java 17: pattern matching for instanceof
if (lockable instanceof Door d) {
d.lock(); // Door locked.
}

}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package bg.sofia.uni.fmi.mjt.lockable;

public class Door implements Lockable, OldLockable {

@Override
public void lock() {
System.out.println("Door locked.");
}

@Override
public boolean isLocked() {
return true;
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package bg.sofia.uni.fmi.mjt.lockable;

public interface Lockable {

void lock();

default boolean isLocked() {
return false;
}

// Static factory method: typical use of static methods in interfaces.
// Keep calm - will learn what Factory is in the Design Patterns lecture
static Lockable getInstance(boolean isDoor) {
if (isDoor) {
return new Door();
} else {
return new Safe();
}
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package bg.sofia.uni.fmi.mjt.lockable;

public interface OldLockable {

default boolean isLocked() {
return true;
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package bg.sofia.uni.fmi.mjt.lockable;

public class Safe implements Lockable, OldLockable {

@Override
public void lock() {
System.out.println("Safe locked.");
}

@Override
public boolean isLocked() {
// We will get a compile-time error, if we don't override the isLocked() method here:
// - "Safe inherits unrelated defaults for isLocked() from types Lockable and OldLockable"
return Lockable.super.isLocked();
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package bg.sofia.uni.fmi.mjt.overridings;

public class Audi extends Car {

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package bg.sofia.uni.fmi.mjt.overridings;

public class AudiGarage extends Garage {

public AudiGarage() {
// Note that parent default constructor will be invoked prior to this one.
// Calling it explicitly with super() here will have the same effect
System.out.println("Audi garage constructed");
}

public static void main(String... args) { // varargs syntax
new AudiGarage();
}

@Override
public Audi repair(Car c) {
// 1. access modifier upgraded from protected to public. Trying to reduce it to private will not compile
// 2. covariant return type: overriden method in parent returns Car
// 3. signature remains identical: otherwise, with the @Override annotation in place, will not compile
return new Audi();
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package bg.sofia.uni.fmi.mjt.overridings;

public class Car {

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package bg.sofia.uni.fmi.mjt.overridings;

public class Garage {

public Garage() {
System.out.println("Garage constructed");
}

protected Car repair(Car c) {
return new Car();
}

public Car repair(Car c, String customerName) {
// overloaded method:
// 1. access modifier may be any
// 2. return type may be any
// 3. name should be identical
// 4. parameter list should be different
return this.repair(c); // "this." is optional here
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
package bg.sofia.uni.fmi.mjt.statics;

class Parent {
void display() {
System.out.println("Non-static method in Parent");
}

static void staticDisplay() {
System.out.println("Static method in Parent");
}
}

class Child extends Parent {
@Override
void display() {
System.out.println("Non-static method in Child");
}

static void staticDisplay() {
System.out.println("Static method in Child (Hidden)");
}
}

public class MethodHidingExample {
public static void main(String[] args) {
Parent parent = new Parent();
Parent childAsParent = new Child();
Child child = new Child();

parent.display(); // Output: Non-static method in Parent
childAsParent.display(); // Output: Non-static method in Child

parent.staticDisplay(); // Output: Static method in Parent; same as calling Parent.staticDisplay();
childAsParent.staticDisplay(); // Output: Static method in Parent, because the reference type is Parent; same as calling Parent.staticDisplay();
child.staticDisplay(); // Output: Static method in Child (Hidden), because the reference type is Child;same as calling Child.staticDisplay();

// In summary - static methods belong to the class and no overriding is possible -
// it's possible to redefine the same method in the child class, but that's not overriding.
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package bg.sofia.uni.fmi.mjt.statics;

public class Project {

private static final String PROJECT_PREFIX = "proj-"; // constant
private static int totalProjectInstances;

private String name;

public Project() {
// We can use static variable to count the number of Project instances created.
// All instances of Project will share the same copy of the variable.

name = PROJECT_PREFIX + totalProjectInstances++;
}

public String getName() {
return name;
}

public static int getTotalProjectInstances() {
return totalProjectInstances;
}

// We cannot use instance variables/methods in static methods because
// static methods are not bound to any instance, but rather to the class itself
// Uncommenting the method below will not compile:
// "non-static variable name cannot be referenced from a static context"

//public static void printName() {
// System.out.println(name);
//}

public static void main(String... s) {
System.out.println(new Project().getName());
System.out.println(new Project().getName());
System.out.println(new Project().getName());
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package bg.sofia.uni.fmi.mjt.suuper;

class Parent {
int parentValue;

Parent(int parentValue) {
this.parentValue = parentValue;
}

void displayParent() {
System.out.println("Parent value: " + parentValue);
}
}

class Child extends Parent {
int childValue;

Child(int parentValue, int childValue) {
super(parentValue); // Call the superclass constructor
this.childValue = childValue;
}

void displayChild() {
System.out.println("Child value: " + childValue);
}

void displayParentAndChild() {
super.displayParent(); // Call the parent class method using super
displayChild();
}
}

public class SuperExample {
public static void main(String[] args) {
Child child = new Child(10, 20);

child.displayParentAndChild();
}
}

0 comments on commit 6abe0f5

Please sign in to comment.