Hands-on Programming Exercises — Ch. 13
GeometricObject with fields color (String) and filled (boolean), a constructor, getters/setters, and two abstract methods: getArea() and getPerimeter(). Create concrete class Circle (field: radius) and Rectangle (fields: width, height) that extend it and implement both abstract methods. In main, create one of each and print their properties.abstract class GeometricObject { String color; boolean filled; GeometricObject(String color, boolean filled){...} public abstract double getArea(); public abstract double getPerimeter(); }. Circle: class Circle extends GeometricObject { double radius; Circle(double radius, String color, boolean filled){ super(color, filled); this.radius = radius; } public double getArea(){ return Math.PI * radius * radius; } public double getPerimeter(){ return 2 * Math.PI * radius; } }. Rectangle follows the same pattern with width * height and 2*(width+height).makeSound() abstract forces every concrete subclass to provide its own sound implementation. This is the core power of abstract methods: enforce a contract without dictating the implementation.Animal with a field name (String), a constructor, an abstract method makeSound(), and a concrete method breathe() that prints "[name] is breathing". Create three concrete subclasses: Dog (prints "Woof!"), Cat (prints "Meow!"), and Bird (prints "Tweet!"). In main, create an array of Animal references and call both methods on each.abstract class Animal { String name; Animal(String name){ this.name = name; } public abstract void makeSound(); public void breathe(){ System.out.println(name + " is breathing"); } }. Dog: class Dog extends Animal { Dog(String name){ super(name); } public void makeSound(){ System.out.println(name + " says: Woof!"); } }. Cat and Bird follow the same pattern with "Meow!" and "Tweet!" respectively.Square and a Triangle are unrelated shapes, but both can be drawn and resized. Interfaces let unrelated classes share a common capability without forcing an inheritance hierarchy. A class can implement multiple interfaces, which is impossible with abstract class inheritance.Drawable with method draw(). Create interface Resizable with method resize(double factor). Create class Square with field side (double) that implements both interfaces: draw() prints the side length and resize(factor) multiplies side by factor. Create class Triangle with field base (double) that also implements both. In main, demonstrate both.interface Drawable { void draw(); } — all methods are implicitly public abstract. Implementing both: class Square implements Drawable, Resizable { double side; Square(double side){ this.side = side; } public void draw(){ System.out.println("Drawing Square with side: " + side); } public void resize(double factor){ side *= factor; System.out.println("Resizing Square by factor " + factor + " \u2192 new side: " + side); } }. Triangle follows the same pattern with base.Arrays.sort() know how to order your objects? It doesn't — unless your class implements Comparable and defines a compareTo() method. Implementing Comparable<T> gives your class a natural ordering that Java's built-in sort methods can use automatically.Student class that implements Comparable<Student>. Fields: name (String) and gpa (double). Implement compareTo(Student other) to sort by GPA in ascending order (return negative if this GPA < other GPA, positive if greater, zero if equal). Use Double.compare(this.gpa, other.gpa). In main, create an array of students, sort with Arrays.sort(), and print them.class Student implements Comparable<Student>. The compareTo method: public int compareTo(Student other) { return Double.compare(this.gpa, other.gpa); } — returns negative when this < other, zero when equal, positive when this > other. toString(): public String toString() { return name + ": " + gpa; }. Then Arrays.sort(students) will automatically use your compareTo.Duck can both fly and swim — two capabilities that come from completely different domains. In Java, a class can only extend one abstract class, but it can implement multiple interfaces. This is the key advantage of interfaces when modeling unrelated capabilities that can be combined.Flyable with method fly(). Create interface Swimmable with method swim(). Create class Duck that implements both: fly() prints "Duck is flying", swim() prints "Duck is swimming". Create class Eagle that implements only Flyable: prints "Eagle is soaring". Create class Fish that implements only Swimmable: prints "Fish is swimming". In main, demonstrate each using interface references.interface Flyable { void fly(); }. Implementing multiple: class Duck implements Flyable, Swimmable { public void fly(){ System.out.println("Duck is flying"); } public void swim(){ System.out.println("Duck is swimming"); } }. Notice Flyable eagle = new Eagle() — an interface reference can hold any object that implements it. This enables polymorphism through interfaces.ElectricCar is a Vehicle (abstract class — shared state and behavior) and can be charged (interface — additional capability). This is the key design rule: use an abstract class for an "is-a" relationship where subclasses share code, and an interface for a "can-do" capability that unrelated classes might share.Vehicle with field brand (String), a constructor, a concrete method startEngine() that prints "Starting [brand] engine", and an abstract method drive(). Create interface Electric with method charge(). Create class ElectricCar that extends Vehicle and implements Electric: drive() prints "Driving silently", charge() prints "Charging battery". Create class GasCar that extends Vehicle only: drive() prints "Driving with engine roar".abstract class Vehicle { String brand; Vehicle(String brand){ this.brand = brand; } public void startEngine(){ System.out.println("Starting " + brand + " engine"); } public abstract void drive(); }. Electric interface: interface Electric { void charge(); }. ElectricCar: class ElectricCar extends Vehicle implements Electric { ElectricCar(String brand){ super(brand); } public void drive(){ System.out.println("Driving silently"); } public void charge(){ System.out.println("Charging battery"); } }. Key: a class can extends one class AND implements one or more interfaces simultaneously.