Home
2Classes, Objects, Instances & Methods
2

Lab Manual II · CSE 202

Classes, Objects, Instances & Methods

Model a real thing as a class with private fields, a constructor and methods; create objects, use getters and setters, a static counter, and see two variables share one object.

← → move between slides · F full screen · M slide list

Before we start

Why this lab

A car park holds hundreds of cars, all different, all built to one design. How does a program describe the design once and make many cars?

The design is a class; each car is an object with its own make, speed and fuel. In this lab you build a Car class and drive two of them.

Lab 2 of 10

Lab at a glance

After this lab you can

  • Explain the difference between a class and an object
  • Define a class with fields, a constructor and methods
  • Create objects with new and call their methods
  • Apply encapsulation with private fields, getters and setters
  • Use this to refer to the current object
  • Use a static field and method for class-level data
  • Show that two reference variables can point to the same object

Before you start

  • Lab 1: program structure, types, decisions and loops
  • Compiling and running Java files from an IDE

Plan for the session

  1. Theory recap
  2. Walk through the program, section by section, and run it
  3. In-lab tasks, shown to the instructor
  4. Report exercises at home

Theory 1 of 5

Class and object

  • A class is a blueprint: it lists the data (fields) and actions (methods) every object will have.
  • An object is a runtime instance made with new; each one has its own copy of the fields.

Theory 2 of 5

Fields, constructor and this

public class Car {
    private String make;
    private int speed;
    private double fuelLevel;

    public Car(String make, double fuelLevel) {
        this.make = make;          // field = parameter
        this.speed = 0;
        this.fuelLevel = fuelLevel;
    }
}
  • A constructor has the class name and no return type; it runs once, when the object is created.
  • this.make is the field of the current object; make alone is the parameter.

Theory 3 of 5

Encapsulation: getters and validating setters

public void setFuelLevel(double fuelLevel) {
    if (fuelLevel >= 0.0 && fuelLevel <= 100.0) {
        this.fuelLevel = fuelLevel;   // invalid values are rejected
    }
}
  • Fields are private: outside code cannot change them directly.
  • Public methods give controlled access, so an object can never hold an invalid fuel level.

Theory 4 of 5

Instance members vs static members

  • Each object has its own make, speed and fuelLevel.
  • private static int count belongs to the class: one copy shared by all cars.
  • Call a static method on the class: Car.getCount().

Theory 5 of 5

References, stack and heap

  • Objects live on the heap; variables on the stack hold references to them.
  • Assigning a reference copies the arrow, not the object: car1 and car3 are aliases.

References, stack and heap

Car car3 = car1;      // no new object!
car3.accelerate(20);
System.out.println(car1.getSpeed());  // changed too

Implementation design

Program design

Implementation design

Execution flow

  1. Create two Car objects; the constructor increments the static count
  2. Print the count with Car.getCount()
  3. Accelerate and brake car1, showing state after each call (speed never goes below 0)
  4. Accelerate and refuel car2 (fuel never exceeds 100)
  5. Read with getters, change make with a setter
  6. Alias car3 = car1 and show the shared speed
  7. Print the final count

Car defines state and behaviour; Lab2Demo only tests it.

Code walkthrough 1 of 10 · Car.java

Fields: instance and static

// Private instance fields
private String make;
private int speed;
private double fuelLevel;

// Static field shared by all Car objects
private static int count = 0;
  • Each Car object gets its own make, speed and fuelLevel.
  • count is static: one copy for the whole class.

Code walkthrough 2 of 10 · Car.java

The constructor

public Car(String make, double fuelLevel) {
    this.make = make;
    this.speed = 0;
    if (fuelLevel >= 0.0 && fuelLevel <= 100.0) {
        this.fuelLevel = fuelLevel;
    } else {
        this.fuelLevel = 0.0;
    }
    count++;
}
  • this.make is the field, make the parameter.
  • Invalid fuel is replaced by 0.0.
  • count++ counts every car created.

Code walkthrough 3 of 10 · Car.java

Behaviour: accelerate and brake

public void accelerate(int delta) {
    if (delta > 0) {
        this.speed = this.speed + delta;
    }
}

public void brake(int delta) {
    if (delta > 0) {
        this.speed = Math.max(0, this.speed - delta);
    }
}
  • Methods change the object’s own state.
  • Math.max(0, …) keeps the speed from going negative.

Code walkthrough 4 of 10 · Car.java

refuel() and display()

public void refuel(double amount) {
    if (amount > 0.0) {
        this.fuelLevel = Math.min(100.0, this.fuelLevel + amount);
    }
}

public void display() {
    System.out.println("-------------------------------");
    System.out.println("Make      : " + make);
    System.out.println("Speed     : " + speed + " km/h");
    System.out.printf("Fuel Level: %.1f%%%n", fuelLevel);
    System.out.println("-------------------------------");
}
  • Math.min(100.0, …) caps the fuel at 100%.
  • %% prints a percent sign in printf.

Code walkthrough 5 of 10 · Car.java

Getters, setters and a static method

// Getter methods
public String getMake() { return make; }
public int getSpeed() { return speed; }
public double getFuelLevel() { return fuelLevel; }

// Setter methods
public void setMake(String make) { this.make = make; }

public void setFuelLevel(double fuelLevel) {
    if (fuelLevel >= 0.0 && fuelLevel <= 100.0) {

Code walkthrough 5 of 10 · Car.java

Getters, setters and a static method (cont.)

        this.fuelLevel = fuelLevel;
    }
}

// Static method
public static int getCount() { return count; }
  • Getters read private fields; the setter validates before changing.
  • getCount() is static: call it as Car.getCount().

Code walkthrough 6 of 10 · Lab2Demo.java

Creating objects

// 1. Object Creation
System.out.println("=== Object Creation ===");
Car car1 = new Car("Sedan", 80.5);
Car car2 = new Car("SUV", 100.0);
System.out.println("Total Car objects created: " + Car.getCount());
  • new runs the constructor twice, so count becomes 2.

Code walkthrough 7 of 10 · Lab2Demo.java

Calling methods on car1

// 2. Method Invocation on car1
System.out.println("\n=== car1 initial state ===");
car1.display();
car1.accelerate(30);
System.out.println("After accelerate(30):");
car1.display();
car1.brake(10);
System.out.println("After brake(10):");
car1.display();
car1.brake(100);
System.out.println("After brake(100):");
car1.display();
  • Every call changes only car1.
  • brake(100) stops at 0, not −80.

Code walkthrough 8 of 10 · Lab2Demo.java

car2 has its own state

// 3. Method Invocation on car2
System.out.println("\n=== car2 initial state ===");
car2.display();
car2.accelerate(60);
car2.refuel(5.0);
System.out.println("After accelerate(60) and refuel(5.0):");
car2.display();
  • car2 is already at 100%, so refuel(5.0) changes nothing.

Code walkthrough 9 of 10 · Lab2Demo.java

Getters and setters in use

// 4. Getters and Setters
System.out.println("\n=== Getters and Setters ===");
System.out.println("car1 make via getter : " + car1.getMake());
System.out.println("car2 speed via getter: " + car2.getSpeed());
car1.setMake("Hatchback");
System.out.println("car1 make after setter: " + car1.getMake());
  • Read through getters, change through the setter.

Code walkthrough 10 of 10 · Lab2Demo.java

Two references, one object

// 5. Reference Semantics
System.out.println("\n=== Reference Semantics ===");
Car car3 = car1;
car3.accelerate(20);
System.out.println("car1.getSpeed() = " + car1.getSpeed());
System.out.println("car3.getSpeed() = " + car3.getSpeed());
System.out.println("car1 and car3 refer to the same object.");

// 6. Static Member
System.out.println("\n=== Static Member ===");
System.out.println("Total Car objects ever created: " + Car.getCount());
  • car3 = car1 copies the reference, not the car.
  • The count is still 2: no object was created.

Step through the code · 1 of 2

Trace: objects, references and a static counter

See the objects on the heap, the references on the stack, and the one shared count.

Step through the code · 1 of 2

Trace: objects, references and a static counter (cont.)

Step through the code · 2 of 2

Trace: methods that guard the object

Each call works on the object this points to. Watch brake(100) and refuel(5.0) refuse to break the rules.

Step through the code · 2 of 2

Trace: methods that guard the object (cont.)

For reference · 2 files

The complete program

public class Car {

    // Private instance fields
    private String make;
    private int speed;
    private double fuelLevel;

    // Static field shared by all Car objects
    private static int count = 0;

    public Car(String make, double fuelLevel) {
        this.make = make;
        this.speed = 0;
        if (fuelLevel >= 0.0 && fuelLevel <= 100.0) {
            this.fuelLevel = fuelLevel;
        } else {
            this.fuelLevel = 0.0;
        }
        count++;
    }

    public void accelerate(int delta) {
        if (delta > 0) {
            this.speed = this.speed + delta;
        }
    }

    public void brake(int delta) {
        if (delta > 0) {
            this.speed = Math.max(0, this.speed - delta);
        }
    }

    public void refuel(double amount) {
        if (amount > 0.0) {
            this.fuelLevel = Math.min(100.0, this.fuelLevel + amount);
        }
    }

    public void display() {
        System.out.println("-------------------------------");
        System.out.println("Make      : " + make);
        System.out.println("Speed     : " + speed + " km/h");
        System.out.printf("Fuel Level: %.1f%%%n", fuelLevel);
        System.out.println("-------------------------------");
    }

    // Getter methods
    public String getMake() { return make; }
    public int getSpeed() { return speed; }
    public double getFuelLevel() { return fuelLevel; }

    // Setter methods
    public void setMake(String make) { this.make = make; }

    public void setFuelLevel(double fuelLevel) {
        if (fuelLevel >= 0.0 && fuelLevel <= 100.0) {
            this.fuelLevel = fuelLevel;
        }
    }

    // Static method
    public static int getCount() { return count; }
}
public class Lab2Demo {

    public static void main(String[] args) {

        // 1. Object Creation
        System.out.println("=== Object Creation ===");
        Car car1 = new Car("Sedan", 80.5);
        Car car2 = new Car("SUV", 100.0);
        System.out.println("Total Car objects created: " + Car.getCount());

        // 2. Method Invocation on car1
        System.out.println("\n=== car1 initial state ===");
        car1.display();
        car1.accelerate(30);
        System.out.println("After accelerate(30):");
        car1.display();
        car1.brake(10);
        System.out.println("After brake(10):");
        car1.display();
        car1.brake(100);
        System.out.println("After brake(100):");
        car1.display();

        // 3. Method Invocation on car2
        System.out.println("\n=== car2 initial state ===");
        car2.display();
        car2.accelerate(60);
        car2.refuel(5.0);
        System.out.println("After accelerate(60) and refuel(5.0):");
        car2.display();

        // 4. Getters and Setters
        System.out.println("\n=== Getters and Setters ===");
        System.out.println("car1 make via getter : " + car1.getMake());
        System.out.println("car2 speed via getter: " + car2.getSpeed());
        car1.setMake("Hatchback");
        System.out.println("car1 make after setter: " + car1.getMake());

        // 5. Reference Semantics
        System.out.println("\n=== Reference Semantics ===");
        Car car3 = car1;
        car3.accelerate(20);
        System.out.println("car1.getSpeed() = " + car1.getSpeed());
        System.out.println("car3.getSpeed() = " + car3.getSpeed());
        System.out.println("car1 and car3 refer to the same object.");

        // 6. Static Member
        System.out.println("\n=== Static Member ===");
        System.out.println("Total Car objects ever created: " + Car.getCount());
    }
}

Copy or download each file, save it under the same name, then compile and run: javac *.java → java Lab2Demo

Implementation

Expected output

car3 = car1 creates no object, so the count stays 2 and both variables report speed 20.

Interactive 1 of 3

Create objects and follow the references

Interactive 2 of 3

Who can see a private field?

Interactive 3 of 3

What can static code use?

In-lab task 1 of 3

Task 1: Extend the Car class

Add an engine to the car: it may only accelerate while the engine is on.
Requirements
Show a hint
Wrap the existing body of accelerate in if (engineOn) { … } else { System.out.println(…); }.

In-lab task 2 of 3

Task 2: Design a BankAccount class

A simple account with an owner, a balance and a count of all accounts.
Requirements
Show a hint
Increment totalAccounts in the constructor, exactly like count in Car.

In-lab task 3 of 3

Task 3: Demonstrate reference sharing

Show that two variables can refer to one BankAccount.
Requirements
Show a hint
Draw the stack and heap first: two arrows, one object.

In-lab tasks

Show your work during the lab

For each task, show the instructor:

  • the source code
  • a successful compilation
  • the running output
  • a short explanation of the logic you used

Lab report · exercise 1 of 2

University student registration

Classes Student, Course and Enrollment (a student enrolled in a course for a semester, with a grade).
Requirements

Lab report · exercise 2 of 2

Retail store inventory

Classes Product and Inventory (an array of products).
Requirements

Lab report

Writing the lab report

  • Problem statement and your design (classes, fields, methods)
  • Complete source code, formatted and commented
  • Sample output or screenshots for normal and edge cases
  • A short discussion: what each OOP concept did in your program

Academic integrity

Copying from the internet, classmates, seniors or any other unauthorized source is strictly prohibited. Full marks may be deducted if plagiarism, copied work or academic dishonesty is detected. Complete the tasks, implementation, output analysis and report yourself.

Discussion and analysis

Viva questions (1 of 2)

Why are the fields of Car private?
Show the answer
Encapsulation: only Car’s own methods can change them, so rules such as “speed never below 0” and “fuel 0–100” are always enforced.
Why is count static but speed is not?
Show the answer
count describes the class (how many cars exist) and must be shared; speed describes one particular car.

Discussion and analysis

Viva questions (2 of 2)

After Car car3 = car1;, how many Car objects exist?
Show the answer
Still two. Only the reference was copied; car1 and car3 point to the same object.
What would happen without this in this.make = make;?
Show the answer
make = make assigns the parameter to itself; the field stays null.

Check yourself

Quiz

Summary

Summary

  • A class is a blueprint; objects are instances created with new.
  • Constructors initialise objects; this names the current object.
  • Private fields + public methods = encapsulation and validation.
  • Static fields and methods belong to the class and are shared.
  • Variables hold references: assignment creates aliases, not copies.