Introduction to Object-Oriented Programming (OOP): Detailed Notes, Examples & Practice Questions (Object Oriented Programming)

Introduction to Object-Oriented Programming: Complete Exam Guide

Hello dear students! Welcome to your first lesson on Object-Oriented Programming. I know some of you might be thinking, “Is this going to be hard?” Do not worry at all. I will explain everything step by step in a way that is easy to understand. By the end of this lesson, you will have a strong foundation for your exam. So let us start with the basics and build up slowly. Are you ready? Good, let us go!

What is Programming?

Before we talk about Object-Oriented Programming, let us first understand what programming itself means. Programming is simply the process of writing instructions that a computer can follow to solve a problem. Think of it like writing a recipe for cooking food. You write down each step clearly so that someone else can follow it and get the same result. In the same way, you write instructions for the computer, and the computer follows them to give you the output you want.

Over the years, the way we write these instructions has changed a lot. In the early days, programmers wrote instructions in a very simple way: one instruction after another, from top to bottom. This is called procedural programming. Later, as programs became bigger and more complex, people needed a better way to organize their code. That is where Object-Oriented Programming came in.

What is Object-Oriented Programming (OOP)?

Object-Oriented Programming, or OOP for short, is a way of writing programs that is based on the idea of objects. Instead of writing a long list of instructions from top to bottom, OOP asks you to think about the real world. You look at the problem you want to solve, and you identify the things (objects) involved in that problem. Then you write code that describes those things and how they interact with each other.

Let me give you a simple example. Suppose you want to write a program for a school management system. In the old procedural way, you would write functions like addStudent(), calculateGrade(), printReport(), and so on. Everything is just a list of actions. But in OOP, you think differently. You ask yourself: what are the main things in a school? Well, there are students, teachers, courses, and classrooms. So you create a Student object, a Teacher object, a Course object, and so on. Each object has its own data and its own behaviors. This makes the program organized, easier to understand, and easier to change later.

Think about it this way. If I ask you to describe a car, you do not just list actions like “start, stop, turn.” You talk about the car itself: it has a color, a model, a speed, and it can start, stop, and turn. The car is the object, its color and model are its data, and starting and stopping are its behaviors. This is exactly how OOP works!

Important Notes to Remember for Exam:
1. OOP stands for Object-Oriented Programming.
2. OOP is based on the concept of objects that contain both data and methods.
3. OOP was developed to handle large and complex software systems better than procedural programming.
4. The main goal of OOP is to make code reusable, maintainable, and organized.
5. Languages that support OOP include Java, C++, Python, C#, and others.
6. Java is a pure object-oriented language (almost everything in Java is an object).
MCQ

Question 1: Object-Oriented Programming is based on which concept?

A) Functions    B) Objects    C) Loops    D) Variables

Answer: B) Objects

OOP is based on the concept of objects. An object is a real-world thing that has data (attributes) and behaviors (methods). The whole idea of OOP is to break down a problem into objects rather than functions. Functions are the focus of procedural programming, not OOP. Loops and variables are just tools used inside any programming style, they are not the basis of OOP.

MCQ

Question 2: Which of the following is a pure object-oriented programming language?

A) C    B) C++    C) Java    D) Pascal

Answer: C) Java

Java is considered a pure object-oriented language because in Java, almost everything is treated as an object. Except for primitive types like int, char, and boolean, everything else must be inside a class. C and Pascal are procedural languages. C++ supports OOP but it also supports procedural programming, so it is a hybrid language, not a pure OOP language.

Now, this is a very important comparison for your exam. Many questions come from understanding the difference between the old way (procedural) and the new way (object-oriented). Let me explain both in detail.

Procedural Programming

In procedural programming, the program is written as a sequence of instructions. The focus is on what to do step by step. The program is divided into functions (also called procedures or subroutines), and data is passed between these functions. Languages like C, Pascal, and Fortran are procedural languages.

Let me give you an example. Suppose you want to calculate the area of different shapes using procedural programming:

// Procedural approach double radius = 5; double area = 3.14159 * radius * radius; print(area); double length = 10; double width = 4; area = length * width; print(area);

Notice how the data (radius, length, width) and the operations (calculations) are separate. The data is just floating around, and any function can change it. This can cause problems in big programs because it becomes hard to track which function changed what data.

Object-Oriented Programming

In OOP, the data and the operations that work on that data are bundled together inside an object. The focus is on who does what. Instead of asking “what step comes next?”, you ask “which object should do this task?”

// Object-Oriented approach class Circle { double radius; double calculateArea() { return 3.14159 * radius * radius; } } class Rectangle { double length; double width; double calculateArea() { return length * width; } }

See the difference? In the OOP version, the data (radius, length, width) and the method (calculateArea) are kept together inside their respective objects. A Circle has its own data and its own way of calculating area. A Rectangle has its own data and its own way. They do not mix with each other. This is much cleaner and safer.

Procedural Programming: Data —–> Function1 —–> Function2 —–> Function3 (data is separate from functions) Object-Oriented Programming: Object1 = [Data1 + Methods1] Object2 = [Data2 + Methods2] Object3 = [Data3 + Methods3] (data and methods are together inside objects)
Important Notes to Remember for Exam:
1. In procedural programming, the focus is on functions. In OOP, the focus is on objects.
2. In procedural programming, data can be accessed by any function (less secure). In OOP, data is hidden inside objects and accessed through methods (more secure).
3. Procedural programming is good for small programs. OOP is better for large and complex programs.
4. OOP supports features like inheritance, polymorphism, and encapsulation that procedural programming does not have.
5. Procedural programming uses a top-down approach. OOP uses a bottom-up approach.
FeatureProcedural ProgrammingObject-Oriented Programming
FocusFunctions (procedures)Objects
Data and functionsSeparateWrapped together inside objects
ApproachTop-downBottom-up
Data securityLow (data is exposed)High (data is hidden/encapsulated)
ReusabilityLimitedHigh (through inheritance)
Best forSmall programsLarge, complex programs
ExamplesC, Pascal, FortranJava, C++, Python, C#
MaintenanceDifficult for large codeEasier due to modularity
MCQ

Question 3: In procedural programming, data and functions are:

A) Wrapped together in objects    B) Kept separate    C) Hidden inside classes    D) Stored in databases

Answer: B) Kept separate

In procedural programming, data and functions exist independently. Data is declared as global or local variables, and functions operate on that data. There is no concept of wrapping data and functions together. Wrapping data and functions together inside objects is the key characteristic of Object-Oriented Programming, not procedural programming. This separation is actually one of the main weaknesses of procedural programming because any function can access and modify data, leading to errors.

MCQ

Question 4: Which approach does Object-Oriented Programming follow?

A) Top-down approach    B) Bottom-up approach    C) Left-to-right approach    D) Random approach

Answer: B) Bottom-up approach

OOP follows a bottom-up approach. This means you first identify the small, basic objects (like Student, Course, Teacher), build them, and then combine them to form the complete system. You start from the bottom (small parts) and build up to the top (complete program). Procedural programming, on the other hand, follows a top-down approach where you break the big problem into smaller functions from top to bottom.

List and Explain

Question 5: List any four differences between procedural programming and object-oriented programming.

Answer:

1. Focus: Procedural programming focuses on writing functions and procedures. OOP focuses on creating objects that contain data and methods.

2. Data security: In procedural programming, data is often global and can be accessed by any function, making it less secure. In OOP, data is encapsulated (hidden) inside objects and can only be accessed through controlled methods, making it more secure.

3. Reusability: Procedural programming has limited code reusability. You often need to copy and paste code. OOP supports reusability through inheritance, where a child class can reuse the code of a parent class.

4. Approach: Procedural programming uses a top-down approach (break big problem into functions). OOP uses a bottom-up approach (identify objects first, then combine them).

The Four Pillars of OOP

Now we come to one of the most important parts of this lesson. Object-Oriented Programming is built on four main ideas, which are called the four pillars of OOP. These four pillars are:

Four Pillars of OOP / | | \ / | | \ v v v v Encapsulation Abstraction Inheritance Polymorphism

Every single OOP concept you will learn in this course is connected to one or more of these four pillars. Let me explain each one in detail now.

Pillar 1: Encapsulation

The word “encapsulation” comes from “capsule.” Just like a medicine capsule keeps the medicine safe inside a covering, encapsulation keeps data safe inside a class by hiding it from the outside world. You cannot touch the data directly. You must use specific methods to access or change it.

In programming terms, encapsulation means binding data (variables) and methods (functions) together inside a class, and hiding the data from outside access. We hide the data by making the variables private, and we provide public methods (called getters and setters) to read and write those variables safely.

Let me give you a real-life example. Think about an ATM machine. When you use an ATM, you do not directly access the bank’s database. You interact with the ATM screen and buttons. You put in your PIN, and the ATM checks if it is correct, then gives you money. The ATM encapsulates the bank’s data. You cannot see or change the data directly, but you can use the ATM’s interface to perform operations safely.

Example of Encapsulation in Java

class Student { // Data is hidden (private) private String name; private int age; private double grade; // Public methods to access and change the data safely public void setName(String n) { name = n; } public String getName() { return name; } public void setAge(int a) { if (a > 0 && a < 120) { // validation age = a; } else { System.out.println("Invalid age!"); } } public int getAge() { return age; } public void setGrade(double g) { if (g >= 0 && g <= 100) { // validation grade = g; } else { System.out.println("Invalid grade!"); } } public double getGrade() { return grade; } } public class Main { public static void main(String[] args) { Student s = new Student(); s.setName("Abebe"); s.setAge(20); s.setGrade(85.5); // s.age = -5; // ERROR! age is private, cannot access directly // s.name = ""; // ERROR! name is private System.out.println("Name: " + s.getName()); System.out.println("Age: " + s.getAge()); System.out.println("Grade: " + s.getGrade()); } }

Look at what happened here. The variables name, age, and grade are declared as private. This means no one from outside the class can directly access them. If someone tries to write s.age = -5, the compiler will give an error. Instead, they must use the setAge() method, which checks if the age is valid before setting it. This is the power of encapsulation: it protects your data from wrong changes.

Important Notes to Remember for Exam:
1. Encapsulation means hiding data inside a class and providing controlled access through methods.
2. Data is made private using the private access modifier.
3. Access to data is provided through public getter and setter methods.
4. Encapsulation allows data validation (like checking if age is positive).
5. Encapsulation makes the code more secure and maintainable.
6. If you change the internal implementation of a class, the outside code does not break (because it uses methods, not direct access).
7. A fully encapsulated class has all private fields and public getter/setter methods.
MCQ

Question 6: Which access modifier is commonly used to hide data in encapsulation?

A) public    B) protected    C) private    D) default

Answer: C) private

The private access modifier is used to hide data in encapsulation. When a variable is declared private, it can only be accessed within the same class. No other class can directly read or modify it. This is the core of encapsulation: hiding the data from the outside world. Public, protected, and default access modifiers all allow some level of external access, so they do not provide the hiding that encapsulation requires.

MCQ

Question 7: What is the main advantage of using setter methods in encapsulation?

A) They make the code run faster    B) They allow data validation before setting a value    C) They reduce the number of variables    D) They make variables public

See also  Classes and Objects in Java: Detailed Notes, Examples & Practice Questions (Object Oriented Programming)

Answer: B) They allow data validation before setting a value

The main advantage of setter methods is data validation. Before assigning a value to a private variable, the setter method can check if the value is valid. For example, a setAge() method can check that age is not negative, a setGrade() method can check that the grade is between 0 and 100. If you allowed direct access to the variable, anyone could set any value, including invalid ones. Setter methods act as a gatekeeper that only allows valid data to pass through.

True or False

Question 8: Encapsulation means making all variables public so they can be easily accessed.

Answer: False

Encapsulation means the exact opposite. It means making variables private so they CANNOT be directly accessed from outside the class. Access is provided only through public methods (getters and setters). Making variables public would defeat the entire purpose of encapsulation, which is to protect and hide data.

Pillar 2: Abstraction

Abstraction is about showing only the essential information and hiding the unnecessary details. The word “abstract” means something that is not concrete, something that is a general idea rather than specific details.

Let me explain with a real-life example. When you drive a car, you know how to use the steering wheel, the brakes, and the accelerator. You press the brake pedal and the car stops. But do you know exactly how the brake fluid flows through the pipes? Do you know how the brake pads press against the disc? Probably not. And you do not need to know! The car manufacturer has abstracted the complex internal details and given you a simple interface (the brake pedal) to use. You only see what you need to see.

In programming, abstraction means hiding the complex implementation details of a class and showing only the essential features to the user. The user knows what the class does, but not how it does it.

Without Abstraction (showing everything): User sees: brake pedal + brake fluid + pipes + brake pads + disc + springs + … With Abstraction (showing only essentials): User sees: [brake pedal] —> car stops (internal details are hidden)

In Java, abstraction is achieved in two ways:

  • Abstract classes (using the abstract keyword)
  • Interfaces (using the interface keyword)

Example of Abstraction

abstract class Smartphone { // Abstract method: only declaration, no body abstract void makeCall(String number); abstract void sendSMS(String number, String message); // Concrete method: has a body void powerOn() { System.out.println(“Phone is turning on…”); } } class Samsung extends Smartphone { void makeCall(String number) { System.out.println(“Samsung: Calling ” + number + ” via LTE network”); } void sendSMS(String number, String message) { System.out.println(“Samsung: Sending SMS to ” + number); } } class iPhone extends Smartphone { void makeCall(String number) { System.out.println(“iPhone: Calling ” + number + ” via 5G network”); } void sendSMS(String number, String message) { System.out.println(“iPhone: Sending iMessage to ” + number); } } public class Main { public static void main(String[] args) { // Smartphone s = new Smartphone(); // ERROR! Cannot create object of abstract class Samsung s = new Samsung(); s.makeCall(“0911223344”); s.powerOn(); iPhone i = new iPhone(); i.makeCall(“0955667788”); } }

In this example, the Smartphone class is abstract. It says every smartphone must be able to make calls and send SMS, but it does not say HOW. The “how” part is left to the child classes (Samsung and iPhone). The user of this code only needs to know that they can call makeCall() and sendSMS(). They do not need to know the internal details of how Samsung or iPhone implements these methods. That is abstraction!

Important Notes to Remember for Exam:
1. Abstraction means showing what a class does, hiding how it does it.
2. Abstraction is achieved using abstract classes and interfaces in Java.
3. An abstract method has no body (just the declaration, ending with a semicolon).
4. A class with at least one abstract method MUST be declared as abstract.
5. You cannot create an object of an abstract class.
6. An abstract class CAN have both abstract methods and concrete (normal) methods.
7. Abstraction reduces complexity by hiding unnecessary details from the user.
MCQ

Question 9: Which of the following is TRUE about abstract methods in Java?

A) They have a body but no name    B) They have a name and parameters but no body    C) They can be called directly from main method    D) They must be declared as static

Answer: B) They have a name and parameters but no body

An abstract method is a method that is declared (it has a name, return type, and parameters) but has NO body. It ends with a semicolon instead of curly braces. For example: abstract void draw();. Abstract methods cannot be called directly because they have no implementation. They must be overridden by a child class that provides the body. Abstract methods are not declared as static; static methods belong to the class and cannot be abstract.

MCQ

Question 10: What happens when you try to create an object of an abstract class?

A) The object is created but methods cannot be called    B) Compile-time error    C) Runtime error    D) The object is created normally

Answer: B) Compile-time error

You cannot create an object of an abstract class. If you try to write something like Smartphone s = new Smartphone(); where Smartphone is abstract, the Java compiler will immediately give an error. This is because an abstract class is incomplete (it has methods without a body). You cannot create an object of something that is incomplete. However, you CAN create an object of a child class that extends the abstract class and provides implementations for all abstract methods.

Short Answer

Question 11: Explain abstraction with a real-life example that is different from the car example above.

Answer: Think about a coffee machine. When you use a coffee machine, you press a button for espresso or another button for cappuccino, and the machine gives you the coffee. You do not know how the water is heated, how the coffee beans are ground, or how the milk is frothed inside the machine. All these complex internal processes are hidden from you. You only see the buttons and the coffee that comes out. The coffee machine abstracts the complex details and provides a simple interface (buttons) for you to use. In programming, abstraction works the same way: the class hides complex implementation and provides simple methods for the user to call.

Pillar 3: Inheritance (Introduction)

Inheritance is the third pillar of OOP. It allows a new class to receive the properties and behaviors of an existing class. Just like a child inherits some traits from their parents (like eye color or height), a child class in programming inherits variables and methods from its parent class.

The main purpose of inheritance is code reusability. Instead of writing the same code again and again in different classes, you write it once in a parent class, and all child classes can use it.

Animal (Parent Class / Superclass) |— name |— age |— eat() |— sleep() | | inherits (extends) | +———+———+ | | v v Dog Cat (Child Classes / Subclasses) |— bark() |— meow() |— fetch() |— scratch() (can also use name, (can also use name, age, eat(), sleep() age, eat(), sleep())

In the example above, Animal is the parent class. It has common properties like name, age, and common behaviors like eat() and sleep(). The Dog and Cat classes inherit from Animal, so they automatically get all those properties and behaviors without writing them again. But each child class also adds its own special behaviors: Dog can bark and fetch, Cat can meow and scratch.

class Animal { String name; void eat() { System.out.println(name + ” is eating.”); } } class Dog extends Animal { void bark() { System.out.println(name + ” says: Woof Woof!”); } } public class Main { public static void main(String[] args) { Dog d = new Dog(); d.name = “Buddy”; // inherited from Animal d.eat(); // inherited from Animal d.bark(); // Dog’s own method } } // Output: // Buddy is eating. // Buddy says: Woof Woof!

Notice how the Dog class never declared the name variable or the eat() method, but we are still using them. This is because Dog inherited them from Animal using the extends keyword.

Important Notes to Remember for Exam:
1. Inheritance means a child class reuses the code of a parent class.
2. The extends keyword is used to create inheritance in Java.
3. The parent class is also called Superclass or Base class.
4. The child class is also called Subclass or Derived class.
5. Inheritance represents an “is-a” relationship. A Dog IS an Animal.
6. Private members of the parent class are NOT directly accessible in the child class.
7. Constructors are NOT inherited (but the child can call them using super()).
8. Java supports single, multilevel, and hierarchical inheritance with classes (NOT multiple inheritance with classes).
Fill in the Blank

Question 12: The _________ keyword is used in Java to create a child class from a parent class.

Answer: extends

The extends keyword is used in Java to establish an inheritance relationship between two classes. For example, class Dog extends Animal means Dog is a child class of Animal. The word “extends” makes sense because the child class is literally extending (adding to) the parent class. The child class has everything the parent has, plus its own additional members.

MCQ

Question 13: Which type of relationship does inheritance represent?

A) Has-a    B) Is-a    C) Uses-a    D) Part-of

Answer: B) Is-a

Inheritance always represents an “Is-a” relationship. If you can say “X IS a Y” and it makes sense, then inheritance is appropriate. For example, “A Dog IS an Animal” makes sense, so Dog can inherit from Animal. “A Car IS a Vehicle” makes sense, so Car can inherit from Vehicle. But “A Student HAS a Book” does not indicate inheritance (that would be composition). Always test with the “is-a” phrase when deciding if inheritance is the right choice.

Pillar 4: Polymorphism (Introduction)

The word “Polymorphism” comes from two Greek words: Poly means “many” and morph means “forms.” So polymorphism means “many forms.” In programming, it means the same thing can take different forms or behave differently in different situations.

Let me give you a simple example. Think about the word “open.” You can open a door, open a book, open a file on your computer, and open a bank account. The same word “open” has many different meanings depending on the context. That is polymorphism in real life!

In programming, polymorphism allows us to use the same method name to perform different tasks. There are two main types:

1. Compile-time Polymorphism (Method Overloading): When a class has multiple methods with the same name but different parameters. The compiler decides which method to call based on the arguments.

class Calculator { int add(int a, int b) { return a + b; } int add(int a, int b, int c) { // same name, different parameters return a + b + c; } double add(double a, double b) { // same name, different type return a + b; } }

2. Runtime Polymorphism (Method Overriding): When a child class provides a new implementation of a method that is already in the parent class. The JVM decides which method to call at runtime based on the actual object type.

class Animal { void makeSound() { System.out.println(“Animal makes a sound”); } } class Dog extends Animal { void makeSound() { // overriding parent method System.out.println(“Dog barks: Woof!”); } } class Cat extends Animal { void makeSound() { // overriding parent method System.out.println(“Cat meows: Meow!”); } } public class Main { public static void main(String[] args) { Animal a1 = new Dog(); Animal a2 = new Cat(); a1.makeSound(); // Dog barks: Woof! a2.makeSound(); // Cat meows: Meow! } }

Notice how the same method name makeSound() produces different outputs depending on the object. When we call a1.makeSound(), the JVM sees that a1 is actually a Dog, so it calls Dog’s version. This decision happens at runtime, which is why it is called runtime polymorphism.

Important Notes to Remember for Exam:
1. Polymorphism means “one interface, multiple implementations.”
2. Compile-time polymorphism is achieved through method overloading (same name, different parameters in the SAME class).
3. Runtime polymorphism is achieved through method overriding (same name and same parameters in parent and child class).
4. In method overloading, the compiler decides which method to call (early binding).
5. In method overriding, the JVM decides which method to call at runtime (late binding).
6. For runtime polymorphism, you need: inheritance, method overriding, and a parent type reference pointing to a child type object.
MCQ

Question 14: Having multiple methods with the same name but different parameters in the same class is called:

A) Method overriding    B) Method overloading    C) Method hiding    D) Method abstraction

Answer: B) Method overloading

Method overloading means having multiple methods in the same class with the same name but different parameters (different number, type, or order of parameters). It is an example of compile-time polymorphism because the compiler decides which version to call based on the arguments you pass. Method overriding, on the other hand, happens between a parent class and a child class with the exact same method signature.

MCQ

Question 15: Runtime polymorphism in Java is achieved through:

A) Method overloading    B) Method overriding    C) Constructor overloading    D) Variable shadowing

Answer: B) Method overriding

Runtime polymorphism is achieved through method overriding. When a child class overrides a method of the parent class, and you use a parent type reference to point to a child type object, the JVM decides at runtime which version of the method to call based on the actual object type. Method overloading is resolved at compile time, not runtime. Constructor overloading and variable shadowing are not related to runtime polymorphism.

Understanding Classes and Objects

Now let me explain the two most basic building blocks of OOP: classes and objects. Everything in OOP revolves around these two concepts, so you must understand them very well.

See also  Packages in Java: Detailed Notes, Examples & Practice Questions (Object Oriented Programming)

What is a Class?

A class is like a blueprint or a template. It is a design plan that describes what an object will look like and what it can do. A class does not exist physically. It is just an idea or a plan on paper.

Think about the blueprint of a house. An architect draws a plan on paper showing how the house will look: how many rooms, where the doors are, where the windows are. But the blueprint itself is not a house. You cannot live in a blueprint. You use the blueprint to build actual houses. In the same way, a class is a blueprint, and you use it to create actual objects.

A class contains two things:

  • Attributes (Fields / Variables): The data or properties that describe the object. For a Student class, attributes would be name, age, studentId, grade, etc.
  • Methods (Behaviors / Functions): The actions that the object can perform. For a Student class, methods would be study(), takeExam(), submitAssignment(), etc.
Class: Student (Blueprint/Template) +———————————-+ | Attributes: | | – name : String | | – age : int | | – studentId : String | | – grade : double | | | | Methods: | | + study() : void | | + takeExam() : void | | + displayInfo() : void | +———————————-+

What is an Object?

An object is a real, living instance of a class. If a class is the blueprint, then an object is the actual house built from that blueprint. You can create many objects from one class, just like you can build many houses from one blueprint. Each object has its own copy of the attributes, but they all follow the same structure defined by the class.

class Student { // Attributes String name; int age; String studentId; // Method void displayInfo() { System.out.println(“Name: ” + name); System.out.println(“Age: ” + age); System.out.println(“ID: ” + studentId); } } public class Main { public static void main(String[] args) { // Creating objects from the Student class Student s1 = new Student(); Student s2 = new Student(); Student s3 = new Student(); // Setting data for each object (each has its own data) s1.name = “Abebe”; s1.age = 20; s1.studentId = “ERT1234”; s2.name = “Tigist”; s2.age = 22; s2.studentId = “ERT5678”; s3.name = “Kebede”; s3.age = 21; s3.studentId = “ERT9012”; // Each object behaves independently s1.displayInfo(); System.out.println(“—“); s2.displayInfo(); System.out.println(“—“); s3.displayInfo(); } }

Output:

Name: Abebe Age: 20 ID: ERT1234 — Name: Tigist Age: 22 ID: ERT5678 — Name: Kebede Age: 21 ID: ERT9012

Look at how s1, s2, and s3 are three separate objects. Each one has its own name, age, and studentId. Changing s1’s name does not affect s2 or s3. They are independent of each other, but they all share the same structure (they all have name, age, studentId, and displayInfo() method) because they were all created from the same Student class.

Class (Blueprint) Objects (Instances) Student s1 s2 s3 +———–+ +———–+ +———–+ +———–+ | name | —> | Abebe | | Tigist | | Kebede | | age | | 20 | | 22 | | 21 | | studentId | | ERT1234 | | ERT5678 | | ERT9012 | | display() | | display() | | display() | | display() | +———–+ +———–+ +———–+ +———–+
Important Notes to Remember for Exam:
1. A class is a blueprint/template. An object is an instance of a class.
2. A class does not occupy memory when it is created (it is just a design). An object occupies memory when it is created using new.
3. You can create many objects from one class.
4. Each object has its own copy of instance variables.
5. The new keyword is used to create an object in Java.
6. The syntax is: ClassName objectName = new ClassName();
7. A class is a logical entity (exists in code). An object is a physical entity (exists in memory).
MCQ

Question 16: Which of the following correctly creates an object of a class called Book?

A) Book b = Book();    B) Book b = new Book();    C) new Book b;    D) Book b = new Book;

Answer: B) Book b = new Book();

In Java, the correct syntax to create an object is ClassName objectName = new ClassName();. The new keyword is required because it allocates memory for the object. Option A is wrong because it is missing the new keyword. Option C has the wrong syntax order. Option D is wrong because it is missing the parentheses () after the constructor name. Always remember: new keyword + class name + parentheses.

MCQ

Question 17: A class is called a blueprint because:

A) It is drawn on paper    B) It defines the structure that objects will follow    C) It is always abstract    D) It has no methods

Answer: B) It defines the structure that objects will follow

A class is called a blueprint because, just like an architectural blueprint defines the structure of a house (number of rooms, door positions, window sizes), a class defines the structure of objects (what attributes they have and what methods they can perform). When you create objects from the class, all objects follow this same structure. The blueprint analogy has nothing to do with being drawn on paper, being abstract, or lacking methods.

Fill in the Blank

Question 18: An object is a _________ entity, while a class is a _________ entity.

Answer: physical; logical

An object is a physical entity because it actually exists in the computer’s memory when created with the new keyword. It occupies space in memory. A class is a logical entity because it exists only in the source code as a definition or template. It does not occupy memory until an object is created from it. Think of it as: the class is the idea, the object is the real thing.

Access Modifiers in Java

Access modifiers are keywords that decide how accessible a class, method, or variable is from other parts of your program. Think of access modifiers like security guards. They control who can see and use different parts of your code. There are four access modifiers in Java:

Access ModifierSame ClassSame PackageSubclass (different package)Everyone
privateYesNoNoNo
default (no keyword)YesYesNoNo
protectedYesYesYesNo
publicYesYesYesYes

Let me explain each one simply:

private: The most restrictive. Only the same class can access it. Nobody else. This is what we use for encapsulation. When you make a variable private, only methods inside that same class can read or change it.

default (package-private): When you do not write any access modifier, Java uses default access. This means the member is accessible within the same package but not outside the package. Think of a package like a folder. Default means “visible within this folder only.”

protected: This is like default, but with one extra permission: subclasses (even in different packages) can also access it. Protected is mainly used with inheritance. A child class can access protected members of its parent, even if they are in different packages.

public: The least restrictive. Everyone can access it. From any class, any package, anywhere in your program. Public methods are the ones that act as the interface of your class.

Important Notes to Remember for Exam:
1. There are four access modifiers: private, default, protected, public.
2. private is the most restrictive, public is the least restrictive.
3. Default access has no keyword. If you write int x; without any modifier, it is default.
4. protected allows access to subclasses even in different packages (default does not allow this).
5. For encapsulation, variables are private and methods are public.
6. A common exam question is to identify which modifier allows access from a subclass in a different package (answer: protected or public).
MCQ

Question 19: A protected method in a parent class can be accessed by:

A) Only the same class    B) Same class and same package only    C) Same class, same package, and subclasses in different packages    D) Any class in any package

Answer: C) Same class, same package, and subclasses in different packages

The protected access modifier allows access from three places: (1) the same class, (2) any class in the same package, and (3) subclasses even if they are in different packages. Option A describes private access. Option B describes default access. Option D describes public access. Protected is unique because it is the only modifier that specifically allows subclass access across packages.

MCQ

Question 20: If you do not write any access modifier before a class member, what is the default access level?

A) private    B) protected    C) public    D) Package-private (same package only)

Answer: D) Package-private (same package only)

When you do not write any access modifier, Java assigns default access, which is also called package-private. This means the member is accessible only within the same package. It is NOT private, protected, or public. It is its own level of access. Many students confuse default with private or public, but remember: default means “visible within this package only, nothing outside.”

Static Keyword in Java

The static keyword is another important concept that appears frequently in exams. Let me explain it clearly.

Normally, when you create a class, each object gets its own copy of the instance variables. If you have 10 Student objects, each one has its own name and age. But sometimes, you need a variable that is shared by all objects of a class. That is where static comes in.

A static variable (also called a class variable) belongs to the class itself, not to any particular object. There is only ONE copy of a static variable, no matter how many objects you create. All objects share that same copy.

A static method belongs to the class, not to objects. You can call a static method using the class name directly, without creating any object.

class Student { String name; // instance variable (each object has its own) static int count = 0; // static variable (shared by all objects) Student(String n) { name = n; count++; // every time an object is created, count increases } void display() { System.out.println(“Name: ” + name); } static void showCount() { // static method System.out.println(“Total students: ” + count); } } public class Main { public static void main(String[] args) { Student s1 = new Student(“Abebe”); Student s2 = new Student(“Tigist”); Student s3 = new Student(“Kebede”); s1.display(); // Name: Abebe s2.display(); // Name: Tigist s3.display(); // Name: Kebede // Calling static method using class name (no object needed) Student.showCount(); // Total students: 3 } }

In this example, count is a static variable. Even though we created three objects, there is only ONE count variable. Every time a Student object is created in the constructor, count is increased by 1. So after creating three objects, count is 3. All three objects share this same count variable.

Important Notes to Remember for Exam:
1. Static variables are shared by all objects of a class. There is only one copy.
2. Static methods can be called using the class name without creating an object.
3. Static methods can NOT directly access instance variables or instance methods (because they do not belong to any object).
4. Static methods can access other static variables and static methods.
5. main() method is static because the JVM needs to call it without creating an object of the class.
6. Static blocks are used to initialize static variables. They run when the class is loaded (before any object is created).
True or False

Question 21: A static method can directly access instance (non-static) variables of the same class.

Answer: False

A static method belongs to the class, not to any object. Instance variables belong to individual objects. Since the static method does not have any object reference, it cannot know which object’s instance variable to access. For example, if there are 10 Student objects, each with a different name, and you call a static method, the static method cannot know which student’s name to access. Therefore, static methods CANNOT directly access instance variables. They can only access static variables and other static methods.

MCQ

Question 22: How many copies of a static variable exist when you create 5 objects of a class?

A) 5    B) 1    C) 0    D) Depends on the variable type

Answer: B) 1

There is always exactly ONE copy of a static variable, no matter how many objects you create. The static variable belongs to the class, not to objects. Whether you create 1 object, 5 objects, or 100 objects, the static variable exists only once in memory and is shared by all objects. This is the fundamental difference between static variables (one copy shared by all) and instance variables (each object gets its own copy).

The “this” Keyword

The this keyword is a reference to the current object inside a class. When you are writing code inside a class and you want to refer to the object that is currently being used or created, you use this.

The most common use of this is to solve the problem when a method parameter has the same name as an instance variable. Let me show you:

class Student { String name; int age; // Without ‘this’ – PROBLEM! Student(String name, int age) { name = name; // assigns parameter to itself, NOT to the instance variable! age = age; // same problem! } // With ‘this’ – CORRECT! Student(String name, int age) { this.name = name; // ‘this.name’ is the instance variable, ‘name’ is the parameter this.age = age; // ‘this.age’ is the instance variable, ‘age’ is the parameter } }

When you write this.name, Java knows you are talking about the instance variable of the current object. When you write just name, Java refers to the parameter (the closest one). So this.name = name means “set the current object’s name variable to the value of the parameter name.” This is a very common pattern in Java, and you will see it everywhere.

MCQ

Question 23: In the statement this.name = name;, what does this.name refer to?

A) The parameter name    B) The instance variable of the current object    C) A local variable    D) A static variable

Answer: B) The instance variable of the current object

In this.name = name;, this.name refers to the instance variable of the current object. The plain name (without this) refers to the method parameter because Java resolves to the closest declaration. So this statement takes the value from the parameter (right side) and assigns it to the instance variable (left side). This pattern is the standard way to avoid confusion when parameter names match instance variable names.

Benefits of Object-Oriented Programming

Now you might ask, “Why should we use OOP instead of procedural programming?” That is a fair question. Let me explain the main benefits of OOP that make it the preferred choice for building large software systems.

1. Code Reusability: Through inheritance, you can write code once in a parent class and reuse it in many child classes. You do not need to write the same code again and again. This saves time and effort.

2. Data Security (Encapsulation): By making data private and providing controlled access through methods, OOP protects your data from being changed accidentally or maliciously by other parts of the program.

3. Easier Maintenance: Because OOP organizes code into separate objects, when you need to fix a bug or add a feature, you usually only need to change one class. You do not have to search through thousands of lines of unrelated code. This makes the program easier to maintain and update.

4. Real-World Modeling: OOP allows you to model real-world entities directly in your code. A Student object in your program can directly represent a student in the real world. This makes the code easier to understand and discuss with non-programmers.

5. Flexibility through Polymorphism: Polymorphism allows you to write flexible code that can work with different types of objects. You can add new types without changing existing code. This makes your program adaptable to future changes.

6. Modularity: OOP naturally divides your program into independent modules (classes and objects). Each class is like a self-contained unit with its own data and methods. This makes development easier because different team members can work on different classes independently.

Important Notes to Remember for Exam:
1. The main benefits of OOP are: reusability, security, maintainability, real-world modeling, flexibility, and modularity.
2. Code reusability is mainly achieved through inheritance.
3. Data security is mainly achieved through encapsulation.
4. Flexibility is mainly achieved through polymorphism.
5. OOP is particularly useful for large, complex software projects with many developers.
6. For very small programs, procedural programming might be simpler and faster to write.
List and Explain

Question 24: List any four advantages of Object-Oriented Programming and briefly explain each.

Answer:

1. Code Reusability: Through inheritance, code written in a parent class can be reused by child classes. This reduces duplication and saves development time.

2. Data Security: Encapsulation allows data to be hidden inside classes and accessed only through controlled methods. This prevents unauthorized or accidental modification of data.

3. Easier Maintenance: Code is organized into separate classes, so bugs can be found and fixed in specific classes without affecting the entire program. Changes in one class do not require changes in other classes.

4. Real-World Modeling: OOP maps directly to real-world entities. Objects in code represent real-world things, making the program easier to understand, design, and discuss with stakeholders.

Exercises with Answers

Exercise 1: Create a class called BankAccount with private attributes for account number, account holder name, and balance. Provide public methods to deposit money, withdraw money (with a check that balance does not go below zero), and display the balance. Write a main method to test all operations. This exercise tests your understanding of encapsulation.
class BankAccount { private String accountNumber; private String accountHolder; private double balance; BankAccount(String accNum, String accHolder, double initialBalance) { accountNumber = accNum; accountHolder = accHolder; if (initialBalance >= 0) { balance = initialBalance; } else { balance = 0; } } void deposit(double amount) { if (amount > 0) { balance = balance + amount; System.out.println(“Deposited: ” + amount); } else { System.out.println(“Invalid deposit amount!”); } } void withdraw(double amount) { if (amount > 0 && amount <= balance) { balance = balance - amount; System.out.println("Withdrawn: " + amount); } else if (amount > balance) { System.out.println(“Insufficient balance!”); } else { System.out.println(“Invalid withdrawal amount!”); } } void displayBalance() { System.out.println(“Account: ” + accountNumber); System.out.println(“Holder: ” + accountHolder); System.out.println(“Balance: ” + balance); } } public class Main { public static void main(String[] args) { BankAccount ba = new BankAccount(“ACC001”, “Abebe Bekele”, 5000); ba.displayBalance(); System.out.println(“—“); ba.deposit(2000); ba.displayBalance(); System.out.println(“—“); ba.withdraw(3000); ba.displayBalance(); System.out.println(“—“); ba.withdraw(5000); // should say insufficient balance ba.displayBalance(); } } // Output: // Account: ACC001 // Holder: Abebe Bekele // Balance: 5000.0 // — // Deposited: 2000.0 // Account: ACC001 // Holder: Abebe Bekele // Balance: 7000.0 // — // Withdrawn: 3000.0 // Account: ACC001 // Holder: Abebe Bekele // Balance: 4000.0 // — // Insufficient balance! // Account: ACC001 // Holder: Abebe Bekele // Balance: 4000.0
Exercise 2: Identify whether the following scenarios represent an “is-a” relationship or a “has-a” relationship, and explain your reasoning: (a) Teacher and School (b) Car and Vehicle (c) Book and Library (d) Dog and Animal

Answer:

(a) Teacher and School: Has-a relationship. A Teacher HAS a School (a teacher works at a school). You cannot say “A Teacher IS a School.” This represents composition, not inheritance.

(b) Car and Vehicle: Is-a relationship. A Car IS a Vehicle. This is a classic example of inheritance. Car can inherit from Vehicle because every car is a type of vehicle.

(c) Book and Library: Has-a relationship. A Library HAS Books. A book is not a library. This represents composition. A Library class might have a list of Book objects as its member.

(d) Dog and Animal: Is-a relationship. A Dog IS an Animal. This is inheritance. Dog can inherit from Animal because every dog is a type of animal.

Rule: If you can say “X IS a Y” and it makes sense, it is an is-a relationship (inheritance). If you can say “X HAS a Y” and it makes sense, it is a has-a relationship (composition).

Exercise 3: What will be the output of the following code? Explain your answer.
class Counter { static int count = 0; int id; Counter() { count++; id = count; } void show() { System.out.println(“ID: ” + id + “, Total: ” + count); } } public class Test { public static void main(String[] args) { Counter c1 = new Counter(); Counter c2 = new Counter(); Counter c3 = new Counter(); c1.show(); c2.show(); c3.show(); } }

Output:

ID: 1, Total: 3 ID: 2, Total: 3 ID: 3, Total: 3

Explanation: The count variable is static, so it is shared by all objects. Each time a Counter object is created, the constructor increases count by 1 and sets the id to the current value of count. The id variable is NOT static, so each object has its own copy. After creating three objects, count is 3 (shared). But each object has its own id: c1 has id=1, c2 has id=2, c3 has id=3. When show() is called, each object prints its own id (different) and the shared count (same = 3 for all).

Exercise 4: Create an abstract class Shape with an abstract method area() and a concrete method describe() that prints “This is a shape.” Create two subclasses Circle and Rectangle that implement area(). Write a main method to create objects and call both methods. This tests your understanding of abstraction.
abstract class Shape { abstract double area(); // abstract method – no body void describe() { // concrete method – has body System.out.println(“This is a shape.”); } } class Circle extends Shape { double radius; Circle(double r) { radius = r; } @Override double area() { return 3.14159 * radius * radius; } } class Rectangle extends Shape { double length; double width; Rectangle(double l, double w) { length = l; width = w; } @Override double area() { return length * width; } } public class Main { public static void main(String[] args) { Circle c = new Circle(5); c.describe(); System.out.println(“Area of circle: ” + c.area()); System.out.println(“—“); Rectangle r = new Rectangle(4, 6); r.describe(); System.out.println(“Area of rectangle: ” + r.area()); } } // Output: // This is a shape. // Area of circle: 78.53975 // — // This is a shape. // Area of rectangle: 24.0

More Practice Questions for Exam Preparation

MCQ

Question 25: Which of the following is NOT a pillar of OOP?

A) Encapsulation    B) Abstraction    C) Compilation    D) Polymorphism

Answer: C) Compilation

The four pillars of OOP are Encapsulation, Abstraction, Inheritance, and Polymorphism. Compilation is a process of converting source code into machine code, not a pillar of OOP. It is a general programming concept that exists in all programming paradigms, not specific to OOP. If you see any option that is not one of the four pillars, that is the answer for “which is NOT a pillar” type questions.

MCQ

Question 26: Which OOP concept allows you to hide complex implementation details and show only essential features?

A) Inheritance    B) Encapsulation    C) Abstraction    D) Polymorphism

Answer: C) Abstraction

Abstraction is the OOP concept that hides complex implementation details and shows only the essential features to the user. Encapsulation is about hiding data (variables) for security. Inheritance is about reusing code. Polymorphism is about one thing having many forms. Abstraction is specifically about hiding complexity and showing simplicity. Think of the car example: you know how to press the brake pedal (essential feature), but you do not need to know how the brake system works internally (hidden complexity). That is abstraction.

MCQ

Question 27: An abstract class can have:

A) Only abstract methods    B) Only concrete methods    C) Both abstract and concrete methods    D) No methods at all

Answer: C) Both abstract and concrete methods

An abstract class can have both abstract methods (methods without a body) and concrete methods (methods with a body). This is one of the key features of abstract classes. It is different from interfaces (in older Java versions) which could only have abstract methods. The concrete methods in an abstract class provide common functionality that all child classes can use, while the abstract methods force each child class to provide its own specific implementation.

Find the Output

Question 28: What will be the output of the following code?

class Test { int x = 10; static int y = 20; void method1() { System.out.println(x + ” ” + y); } static void method2() { // System.out.println(x); // this line would cause error System.out.println(y); } } public class Main { public static void main(String[] args) { Test t = new Test(); t.method1(); Test.method2(); } }

Output:

10 20 20

Explanation: In method1() (an instance method), both x (instance variable) and y (static variable) can be accessed, so it prints “10 20”. In method2() (a static method), only y (static variable) can be accessed. The line that tries to access x is commented out because it would cause a compile error. Static methods cannot access instance variables. The output of method2() is just “20”. Also notice that method2() is called using the class name Test.method2() because it is a static method.

Short Answer

Question 29: What is the difference between a class and an object? Give at least three differences.

Answer:

1. Nature: A class is a logical entity (it exists only in code as a template). An object is a physical entity (it exists in memory when created).

2. Memory: A class does not occupy memory when it is defined. An object occupies memory when it is created using the new keyword.

3. Creation: A class is defined once using the class keyword. Multiple objects can be created from one class.

4. Analogy: A class is like a blueprint of a house. An object is like an actual house built from that blueprint.

Find the Error

Question 30: Find and explain the error in the following code:

class Student { private String name; public static void main(String[] args) { Student s = new Student(); s.name = “Abebe”; System.out.println(s.name); } }

Error: The line s.name = "Abebe"; will cause a compile-time error.

Explanation: The variable name is declared as private. Private members can only be accessed within the same class. Even though the code is inside the Student class (so it is in the same class), the access is through an object reference s.name. Actually, wait. In Java, private members CAN be accessed within the same class even through an object reference. So this code would actually compile and run fine! Let me correct myself. The code is inside the same class, so private access is allowed. There is actually NO error in this code. This is a trick question. If the code were in a DIFFERENT class, then s.name would be an error because name is private.

Final Exam Tips:
1. The four pillars of OOP (Encapsulation, Abstraction, Inheritance, Polymorphism) are guaranteed to appear in your exam. Know the definition and example of each.
2. Be ready to explain the difference between procedural and object-oriented programming with a clear table.
3. Know the difference between a class and an object. Many questions are built around this basic concept.
4. Memorize the access modifier table (private, default, protected, public) and who can access what.
5. Understand static vs non-static: static belongs to the CLASS, non-static belongs to the OBJECT.
6. Practice writing simple classes with private variables and public getter/setter methods (encapsulation).
7. Remember: abstract methods have NO body, and you CANNOT create objects of abstract classes.
8. The “is-a” vs “has-a” test is a very common exam question. Always apply the phrase to check.
9. When you see code with this, understand that it refers to the current object’s instance variable.
10. Practice finding output of code without running it. Many exam questions give you code and ask for the output.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top