Back to Week 4
Lab Session

Week 4: Lab — OOP Basics

Hands-on Programming Exercises — Ch. 9

Progress0 / 5 completed

1Create a Rectangle Class

Think about it: A graphics program needs to represent rectangles. Each rectangle has a width and a height, and you need to compute its area and perimeter. Instead of juggling separate variables for every rectangle, you can define a class — a blueprint that bundles the data and behavior together. Then you just create objects from it!
Create a class called Rectangle with two data fields: width and height (both double). Add a no-arg constructor that sets both to 1.0, and a parameterized constructor that takes width and height. Add methods getArea() and getPerimeter(). In main, create two rectangles and print their areas and perimeters.
Expected OutputRectangle 1: width=1.0, height=1.0 Area: 1.0, Perimeter: 4.0 Rectangle 2: width=4.0, height=5.0 Area: 20.0, Perimeter: 18.0
Your Code
No-arg constructor: Rectangle() { width = 1.0; height = 1.0; }. Parameterized: Rectangle(double width, double height) { this.width = width; this.height = height; }. In main: Rectangle r1 = new Rectangle(); and Rectangle r2 = new Rectangle(4.0, 5.0);.

2Encapsulate a Student Class

Think about it: A university system stores student data — name and GPA. If the GPA field is public, someone could accidentally set it to -5.0 or 99.0. That's invalid! By making the field private and using a setter with validation, you ensure only valid values (0.0 to 4.0) are accepted. This is encapsulation in action.
Create a Student class with private fields: name (String) and gpa (double). Add a constructor that takes both values. Add getters for both fields, and a setter for gpa that only accepts values between 0.0 and 4.0. In main, create a student, try setting an invalid GPA, and show that it doesn't change.
Expected OutputName: Ali, GPA: 3.5 Setting GPA to 5.0... Name: Ali, GPA: 3.5 Setting GPA to 3.9... Name: Ali, GPA: 3.9
Your Code
Declare: private String name; private double gpa;. Constructor: Student(String name, double gpa) { this.name = name; this.gpa = gpa; }. Setter: public void setGpa(double gpa) { if (gpa >= 0.0 && gpa <= 4.0) this.gpa = gpa; }. In main: Student s = new Student("Ali", 3.5);.

3Count Objects with a Static Variable

Think about it: A car rental company wants to know how many Car objects have been created in their system at any point. Each individual car has its own brand and year, but the count should be shared across all cars — it doesn't belong to any single car. This is the perfect use case for a static variable: one copy shared by the entire class.
Create a Car class with instance fields brand (String) and year (int), and a static field count initialized to 0. In each constructor, increment count. Add a static method getCount(). In main, create 3 cars and print the count after each creation.
Expected OutputCreated: Toyota 2022 — Total cars: 1 Created: Honda 2023 — Total cars: 2 Created: BMW 2024 — Total cars: 3
Your Code
Fields: String brand; int year; static int count = 0;. Constructor: Car(String brand, int year) { this.brand = brand; this.year = year; count++; }. Static method: public static int getCount() { return count; }. In main: Car c1 = new Car("Toyota", 2022);.

4BankAccount — Deposit & Withdraw

Think about it: A banking app manages accounts. Each account has an owner name and a balance. You should be able to deposit and withdraw money — but a withdrawal should be rejected if it exceeds the balance (no overdrafts!). This exercise combines encapsulation (private balance), the this keyword, and validation logic inside methods.
Create a BankAccount class with private fields owner (String) and balance (double). Use this in the constructor. Add methods: deposit(double amount) — adds to balance (only if amount > 0), withdraw(double amount) — subtracts from balance (only if amount > 0 and amount <= balance), and getBalance(). Print a message for rejected withdrawals.
Expected OutputOwner: Sara, Balance: 1000.0 After deposit 500.0: Balance: 1500.0 After withdraw 200.0: Balance: 1300.0 Withdraw 2000.0: Insufficient funds! Balance: 1300.0
Your Code
Fields: private String owner; private double balance;. Constructor: BankAccount(String owner, double balance) { this.owner = owner; this.balance = balance; }. Withdraw: public void withdraw(double amount) { if (amount > 0 && amount <= balance) balance -= amount; else System.out.println("Insufficient funds!"); }. In main: BankAccount acc = new BankAccount("Sara", 1000.0);.

5Product Inventory System

Think about it: A small shop needs a simple inventory system. Each product has a name, price, and quantity. You need to be able to sell items (decrease quantity) and restock them (increase quantity). You also want to track how many product types exist using a static counter. This exercise brings together everything from this week: classes, constructors, encapsulation, this, and static members.
Create a Product class with private fields: name, price, quantity, and a static productCount. Add a constructor (use this), getters, a sell(int qty) method (reject if not enough stock), a restock(int qty) method, and a toString() method. Create an array of 3 products, perform operations, and display the inventory.
Expected OutputTotal product types: 3 --- Inventory --- Product: Laptop, Price: 999.99, Stock: 10 Product: Mouse, Price: 29.99, Stock: 50 Product: Keyboard, Price: 79.99, Stock: 30 Selling 3 Laptops... Selling 100 Mice... Not enough stock! Restocking 20 Keyboards... --- Updated Inventory --- Product: Laptop, Price: 999.99, Stock: 7 Product: Mouse, Price: 29.99, Stock: 50 Product: Keyboard, Price: 79.99, Stock: 50
Your Code
Constructor: Product(String name, double price, int quantity) { this.name = name; this.price = price; this.quantity = quantity; productCount++; }. Sell: public void sell(int qty) { if (qty <= quantity) quantity -= qty; else System.out.println("Not enough stock!"); }. Array: Product[] products = { new Product("Laptop", 999.99, 10), new Product("Mouse", 29.99, 50), new Product("Keyboard", 79.99, 30) };. Use for (Product p : products) System.out.println(p); to print.