Prepare for your OOPs interview with our comprehensive list of OOPs interview questions for freshers and experienced candidates.
OVERVIEW
Object-Oriented Programming (OOP) is a key concept that you’re expected to know if you come from a technical background. To help you nail your next interview, we’ve compiled the top 100+ OOPs interview questions and answers to help you master the essential concepts and techniques.
Note : We have compiled all OOPs Interview Questions for you in a template format. Check it out now!
Here are the OOPs interview questions and answers for freshers that cover the fundamental concepts of Object-Oriented Programming, such as inheritance, polymorphism, encapsulation, and abstraction.
This is one of the most commonly asked OOPs interview questions. Object-Oriented Programming is a programming paradigm that uses objects instead of functions and procedures. These objects are grouped into classes. OOP incorporates real-world entities like inheritance, polymorphism, and encapsulation into programming, allowing for the integration of data and methods.
OOPs need to be used for several reasons:
This is a frequently asked OOP interview question. Some major Object-Oriented Programming languages include:
The following are the main features of OOPs:
An object in Object-Oriented Programming is a fundamental unit representing real-world entities. It is an instance of a class, with memory allocated only upon instantiation (object creation). Objects possess identity, state, and behavior, containing data and code to manipulate it. Interaction between objects doesn't require knowledge of each other's data or code specifics, just the types of messages accepted and responses provided.
A class is a user-defined data type that consists of data members and member functions accessible through an instance of the class. It represents the common properties or methods of all objects of a specific type, functioning as a blueprint for an object.
This is one of the most commonly asked OOPs interview questions. Here are the differences between a class and a structure:
Feature | Class | Structure |
---|---|---|
Access Modifiers | Supports public, private, and protected access modifiers. | Typically only supports public access modifiers (implementation-dependent). |
Inheritance | Supports inheritance (single or multiple, depending on the language). | Does not support inheritance (except in C++, where it supports single inheritance). |
Constructor/Destructor | Has constructors and destructors. | Does not have constructors or destructors. |
Method Overloading | Supports method overloading. | Supports method overloading (implementation-dependent). |
Method Overriding | Supports method overriding (in case of inheritance). | Does not support method overriding. |
Default Members | Members are private by default (in most languages). | Members are public by default. |
Size | Can have a size larger than the sum of its members (due to additional metadata). | Size is equal to the sum of its members' sizes. |
Memory Allocation | Objects are typically allocated on the heap. | Structures are typically allocated on the stack or embedded in other data structures. |
Recommended Usage | Used for complex data types and to model real-world entities. | Used for simple, lightweight data types and grouping-related data. |
The primary differences between a class and an object in Object-Oriented Programming are:
Aspect | Class | Object |
---|---|---|
Definition | A class is a template or blueprint that defines the attributes and actions of objects. | An object is a specific instance of a class created from the class blueprint. |
Memory Allocation | A class itself does not occupy any memory space. | Objects occupy memory space when they are created. |
Creation | Classes are created by the programmer during the design phase. | Objects are created from classes at runtime, typically using constructors or object creation expressions. |
Properties and Methods | A class defines the properties and methods that objects will have. | An object has its own copies of the properties and can access and modify them. It also has access to the methods defined in the class. |
Instantiation | A class cannot be instantiated directly. | Objects can be instantiated from a class using the new keyword or object creation expressions. |
Purpose | A class serves as a blueprint or template. | Objects are the actual entities that exist and perform tasks during runtime. |
Access Modifiers | Classes can have access modifiers (public, private, protected) that control access to their members. | Objects do not have access modifiers; they access members based on the access modifiers defined in the class. |
Inheritance | Classes can inherit properties and methods from other classes through inheritance. | Objects cannot inherit directly from other objects but from the class they are instantiated from. |
Polymorphism | Classes support polymorphism, allowing objects of different classes to be treated as objects of a common superclass. | Objects can exhibit polymorphic behavior based on the class they are instantiated from. |
Some of the primary advantages of OOPs are as follows:
Here are the main differences between them:
Aspect | Object-Oriented Programming | Structured Programming |
---|---|---|
Approach | OOP focuses on creating objects that contain data and behavior. The program is organized around objects and their interactions. | Structured Programming focuses on writing a set of instructions or functions to perform tasks. The program is organized around procedures or functions. |
Data and Functions | In OOP, data and functions are combined into objects. Data is encapsulated within objects, and functions (methods) operate on that data. | In Structured Programming, data and functions are separate entities. Functions operate on data passed as arguments. |
Code Organization | Code is organized around classes and objects, promoting code reuse and modularity. | Code is organized around procedures or functions, often leading to monolithic and less modular code. |
Data Abstraction | OOP supports data abstraction and encapsulation, where implementation details are hidden from the user. | Structured Programming has limited support for data abstraction and encapsulation. |
Inheritance | OOP supports inheritance. | Structured Programming does not support inheritance. |
Polymorphism | OOP supports polymorphism. | Structured Programming does not support polymorphism. |
Code Reuse | OOP promotes code reuse through the inheritance and composition of objects. | Structured Programming has limited code reuse capabilities, often achieved through function libraries or modules. |
This is one of the most commonly asked OOPs interview questions. Programming paradigms categorize programming languages based on their core characteristics.
There are two main types:
These paradigms can be further subdivided:
The following are the differences between Procedural Programming and Object-Oriented Programming:
Aspect | Procedural Programming | Object-Oriented Programming |
---|---|---|
Data | Separate from procedures | Encapsulated within objects |
Program structure | Top-down approach | Divided into objects |
Data access | Usually global | Private (encapsulated) |
Code reusability | Limited, mainly through functions | High, through inheritance |
Data security | Less secure | More secure due to encapsulation |
Overloading | Generally not supported | Supports function and operator overloading |
Complexity | Simpler for small programs | Better for managing complex programs |
Modularity | Less modular | Highly modular |
Abstraction level | Low level of abstraction | High level of abstraction |
Inheritance | Not supported | Supported |
Polymorphism | Not supported | Supported |
Examples | C, Pascal | Java, C++, Python, C# |
This is a popular OOP interview question. As the name indicates, access specifiers are special types of keywords used to specify or control the accessibility of entities such as classes and methods.
The three primary access specifiers are:
When to use each:
Think of encapsulation like a capsule. You see a simple shell on the outside, but inside, it contains everything needed to do its job. In programming, encapsulation works similarly:
This is one of the frequently encountered OOPs interview questions. A typical OOPs interview question, this one is often asked. Abstraction in Object-Oriented Programming hides non-essential information and shows only what is necessary to users. This is key to representing real-world objects simply for easy user interaction.
There are two types of abstractions in Object-Oriented Programming:
This is a common OOPs interview question that is regularly asked. Here are a few best practices for using abstraction in your code:
This is one of the most commonly asked OOPs interview questions. Polymorphism is a core concept in Object-Oriented Programming that allows objects of various types to be treated in a uniform way. It makes code more flexible and reusable. It allows for writing methods that can work with objects of multiple types as long as they share a common superclass or interface.
For example, you could have a method that processes "Shape" objects, and it would work correctly whether you pass it a "Circle," "Square," or "Triangle" object, as long as they're all subclasses of "Shape."
There are two main types of polymorphism in Object-Oriented Programming:
When a class has multiple methods with the same name but different parameters, it is called Method Overloading.
Characteristics of method overloading:
Let’s understand this with an example in Java:
class Calculator {
public int add(int a, int b) {
return a + b;
}
public int add(int a, int b, int c) {
return a + b + c;
}
public double add(double a, double b) {
return a + b;
}
}
This is a standard OOPs interview question. When a subclass (child class) in Java implements a method that has the same name and parameters as a method in its parent class, this is called method overriding.
Characteristics of method overriding:
Let’s understand this with an example in Java:
class Shape {
double getArea() {
return 0;
}
}
class Circle extends Shape {
private double radius;
Circle(double radius) {
this.radius = radius;
}
@Override
double getArea() {
return Math.PI * radius * radius;
}
}
class Rectangle extends Shape {
private double width, height;
Rectangle(double width, double height) {
this.width = width;
this.height = height;
}
@Override
double getArea() {
return width * height;
}
}
public class Main {
public static void main(String[] args) {
Shape shape1 = new Circle(5);
Shape shape2 = new Rectangle(4, 6);
System.out.println("Circle area: " + shape1.getArea());
System.out.println("Rectangle area: " + shape2.getArea());
}
}
This is one of the most commonly asked OOPs interview questions. Here's the difference between overloading and overriding:
Aspect | Overloading | Overriding |
---|---|---|
Definition | Methods with identical names and differing parameters. | Implementing a method in a subclass that is already defined in its superclass. |
Purpose | Provides method implementation flexibility. | Allows subclasses to provide specific implementation. |
Class | Occurs within the same class or between parent and child classes. | Occurs between superclass and subclass. |
Method Signature | Must have different parameter types or a number of parameters. | Must have the same method signature (name and parameters). |
Return Type | Can be different | Must be the same or covariant |
Access Modifier | Can be different | Cannot be more restrictive in the subclass |
Static/Non-static | Can be either | Must be non-static |
Binding | Compile-time (static) binding | Runtime (dynamic) binding |
Here's the difference between compile-time polymorphism and runtime polymorphism:
Aspect | Compile-Time Polymorphism | Runtime Polymorphism |
---|---|---|
Resolution Time | Compile time | Runtime |
Also Known As | Static binding, early binding | Dynamic binding, late binding |
Implementation | Method overloading, operator overloading | Method overriding, Inheritance |
Flexibility | Less flexible | More flexible |
Performance | Generally faster | Slightly slower due to runtime resolution |
Decision Making | Before program execution | During program execution |
Type Checking | Done by compiler | Done at runtime |
No, runtime polymorphism cannot be achieved by data members in languages like Java or C++ because:
Inheritance in Object-Oriented Programming describes the ability of a class to inherit features from a superclass.
Syntax:
class SubClass extends SuperClass {
// SubClass members
}
Key elements of the syntax:
The superclass is the class that provides features inherited by a subclass, also known as the base class or parent class.
A subclass is a class that inherits all members (fields, methods, and nested classes) from another class, also known as a derived class, child class, or extended class.
This is a common OOPs interview question that is regularly asked. In Object-Oriented Programming, inheritance is categorized by the relationship between the derived class and its superclass.
This is one of the frequently encountered OOPs interview questions. Despite its strength in Object-Oriented Programming, inheritance does have its set of limitations:
Inheritance is an essential feature in Object-Oriented Programming languages like Java and C++.
Inheritance is like a parent passing traits to their child. In programming, it lets one class (the child) get all the characteristics and abilities of another class (the parent). This means the child class can use the parent's data and functions without rewriting them.
The main idea is to make new classes based on existing ones. The new class (child) gets everything from the old class (parent) and can add its unique features.
With inheritance, we'd save time writing the same code repeatedly for similar classes. It's like reinventing the wheel each time instead of just using a wheel that already exists.
Inheritance can be implemented by using:
It's not possible for a class to extend itself.
Composition is a design approach in Object-Oriented Programming to establish a has-a relationship between objects. In Java, this is done by including instance variables of other objects within a class.
Aggregation: Aggregation represents a weak association between two entities where one entity can contain or use another, but the contained entity can exist independently. It's characterized by:
Example in Java:
Composition: Composition denotes a strong, whole-part relationship between two entities where the part cannot exist without the whole.
Key characteristics include:
Example in Java:
The major differences include:
Following are the differences between inheritance and polymorphism:
Aspect | Inheritance | Polymorphism |
---|---|---|
Definition | A mechanism where a class inherits properties and behaviors from another class. | Objects of different types that are treated as objects of a common base type. |
Purpose | Code reuse and establishing a hierarchical relationship between classes. | Flexibility in using different object types through a common interface. |
Relationship | Establishes an "is-a" relationship between classes. | Enables "one interface, multiple implementations". |
Implementation | Achieved using the extends keyword (in many languages). | Achieved through method overriding and interfaces/abstract classes. |
Types | Single inheritance, multiple inheritance (in some languages). | Runtime polymorphism, compile-time polymorphism. |
Coupling | Creates tight coupling between parent and child classes. | Promotes loose coupling through abstraction. |
Focus | Emphasizes sharing of code and behavior. | Emphasizes interchangeability of objects. |
Often asked, this OOPs interview question is common. In Object-Oriented Programming languages like C#, instance methods of a base class are tied to specific objects and cannot be invoked without an instance. This means you typically need to create an object of either the base class or a derived class to call these methods. However, static methods in a base class operate at the class level rather than the instance level. These can be called directly using the class name, without the need to instantiate an object.
Constructors are special methods or functions in Object-Oriented Programming used to initialize class objects, defining their initial state and creation method. They typically share the same name as their class.
Constructors in Java are classified into three types:
The purpose of a default constructor is to:
Constructors are special functions in Object-Oriented Programming that initialize newly created objects. Unlike regular methods, constructors don't have a return type and are implicitly called when an object is instantiated. Their primary purpose is to set up the initial state of an object by initializing instance variables.
Constructors share the same name as their class and can be overloaded to accept different parameters. While they resemble methods in some ways, constructors are distinct in that they can't be directly called and aren't part of the object's interface.
Many languages provide a default no-argument constructor if none is explicitly defined, and constructors can often chain to other constructors or superclass constructors to build complex initialization sequences.
Yes, we can overload constructors in a class. Constructor overloading indeed works similarly to function overloading. The key aspects are:
Here's an example demonstrating constructor overloading in Java:
This example shows three overloaded constructors for the Rectangle class:
The appropriate constructor is automatically called based on the arguments provided when creating new Rectangle objects.
Constructor chaining in Object-Oriented Programming is the method of using one constructor to invoke another within the same class. This approach helps simplify the program by minimizing redundant code.
Constructor chaining can be achieved in two ways:
Constructors and methods are fundamental components of Object-Oriented Programming, but they serve different purposes and have distinct characteristics.
Person person = new Person();
person.setName("peter");
Here is an example demonstrating the differences between a constructor and a method:
public class Example {
private String name;
private int age;
// Constructor
public Example(String name, int age) {
this.name = name;
this.age = age;
}
// Method
public void displayInfo() {
System.out.println("Name: " + name + ", Age: " + age);
}
public static void main(String[] args) {
// Creating an object using the constructor
Example example = new Example("Jimmy", 30);
// Calling a method on the created object
example.displayInfo();
}
}
A destructor in Object-Oriented Programming is a method that is triggered automatically right before an object's memory is deallocated. This can happen when the object’s scope ends, is contained within another object whose lifetime ends, or is dynamically allocated and explicitly freed.
Note : Test your web and mobile apps across 3000+ real desktop browsers. Leading digital experience testing for insurance sector.
Studying the Scrum Master interview questions outlined in this tutorial will equip you with the right approach to effectively prepare for this job role.
There are two methods to implement abstraction in Java:
An abstract class is a template definition of methods and variables for a particular class or category of objects. In programming, objects are code units, and each object belongs to a generic class.
Abstract classes contain one or more abstract methods or behaviors. Abstracting objects or classes means summarizing their characteristics relevant to the current program's operation. Abstract classes are utilized in all Object-Oriented Programming languages, including Java, C++, C#, and VB.NET.
In Object-Oriented Programming, an interface is a contract that defines a set of abstract methods and constants that a class must implement. It serves as a blueprint for classes, specifying what methods should be available without dictating how these methods should be implemented.
Characteristics of interface include:
This is one of the frequently encountered OOPs interview questions. The reason is that abstract classes can contain non-final variables, while variables in an interface are final, public, and static.
interface SimpleInterface {
int CONSTANT = 100; // implicitly public, static, and final
}
abstract class SimpleAbstractClass {
int variable = 100; // can be non-final and instance-specific
}
The above example shows that interfaces can only have constants, while abstract classes can have mutable instance variables.
The following table demonstrates the difference between an abstract class and interface.
Characteristic | Abstract Class | Interface |
---|---|---|
Variables | Can have non-final instance variables. | Only constants (public static final). |
Methods | Can have both abstract and concrete methods. | All methods are implicitly abstract (before Java 8). |
Constructor | Can have constructors. | Cannot have constructors. |
Multiple Inheritance | A class can extend only one abstract class. | A class can implement multiple interfaces. |
Access Modifiers | Can use any access modifier for members. | All members are implicitly public. |
Instantiation | Cannot be instantiated. | Cannot be instantiated. |
Purpose | For objects that are closely related. | For unrelated classes to implement common behavior. |
Speed | Slightly faster | Slightly slower due to extra indirection. |
Default Method Implementation | Supported | Supported (from Java 8 onwards) |
Static Methods | Can have static methods | Can have static methods (from Java 8 onwards) |
Private Methods | Can have private methods | Can have private methods (from Java 9 onwards). |
No, you cannot declare an interface method as static in most Object-Oriented Programming languages, including Java and C#. Interface methods are, by default, abstract and public. Static methods belong to the class itself, not to any specific instance. The purpose of an interface is to define a contract that implementing classes must follow, which involves instance methods.
However, there are some exceptions:
No, constructors cannot be made static in most Object-Oriented Programming languages, including Java and C#.
Constructors are specifically designed to initialize new object instances when they are created. They set up the initial state of an object and are called automatically when an object is instantiated using the new keyword.
Static members, on the other hand, belong to the class itself rather than to any specific instance of the class. They can be accessed without creating an object of the class.
Making a constructor static would contradict its fundamental purpose of initializing individual object instances. It would also conflict with object creation and initialization in Object-Oriented Programming.
If you need class-level initialization, most languages provide other mechanisms like static initializer blocks or static methods that can be used for this purpose.
This is one of the frequently encountered OOPs interview questions. These are the rules to follow while creating constructors:
No, you cannot declare abstract methods as static in Java due to the inherent contradictions between the concepts of abstract and static methods.
No, an abstract method cannot be private because it must be implemented in the child class.
Declaring it as private would prevent it from being accessed and implemented outside the class.
In Object-Oriented Programming, such as C++, a virtual function or method is an inheritable and overridable function dispatched dynamically. Virtual functions play a crucial role in runtime polymorphism in OOP, enabling the execution of target functions that are not precisely identified at compile time.
Many programming languages, including JavaScript, PHP, and Python, treat all methods as virtual by default and do not offer a modifier to alter this behavior. However, specific languages provide modifiers like final and private in Java and PHP to prevent methods from being overridden by derived classes.
Abstract classes in Object-Oriented Programming have several key characteristics:
Here are the differences between a copy constructor and an assignment operator:
Aspect | Copy Constructor | Assignment Operator |
---|---|---|
Purpose | Creates a new object as a copy of an existing one. | Copies contents of one object to an existing object. |
When it's called | When a new object is created. | When an existing object is assigned a new value. |
Syntax (C++) | ClassName(const ClassName& other) | ClassName& operator=(const ClassName& other) |
Returns | Nothing (constructs a new object). | Reference to the assigned object (usually). |
Self-assignment check | Not needed | Often needed to handle a = a case. |
Memory allocation | Always allocates new memory. | May or may not allocate new memory. |
Usage with new | Can be used with new. | Cannot be used with new. |
Inheritance behavior | Compiler-generated version is called the base class version. | Compiler-generated version doesn't call the base version. |
Default implementation | Performs shallow copy. | Performs shallow copy. |
Abstraction and encapsulation are important concepts in programming. They're related but serve different purposes:
The memory occupied by a class depends on several factors:
The actual memory usage can be larger than the sum of the sizes of data members due to:
Coupling in Object-Oriented Programming refers to the degree of interdependence between classes or modules in a software system. It measures how closely connected or dependent different components are on each other.
There are two types of coupling:
Difference between tight coupling and loose coupling:
Cohesion in OOP refers to the degree to which the elements within a module or class belong together and work towards a single, well-defined purpose. It measures how closely related and focused the responsibilities of a single module or class are.
The operators that cannot be overloaded in C++ are:
Manipulators in Object-Oriented Programming, particularly in C++, are special functions or objects that modify input/output streams. They work by altering the formatting or behavior of streams without changing the actual data.
Manipulators work by modifying the state or behavior of input/output streams:
A real-world example of polymorphism can be found in a digital media player application. Let's consider a music player that can handle various types of audio files:
Each derived class inherits from AudioFile but implements the play() method differently due to the specific encoding and decoding requirements of each file format.
In the application:
//cpp
vector<AudioFile*> playlist;
playlist.push_back(new MP3File("Song1.mp3"));
playlist.push_back(new WAVFile("Song2.wav"));
playlist.push_back(new AADFile("Song3.aad"));
for (AudioFile* song : playlist) {
song->play(); // Polymorphic call
}
Here, the play() method is called on each song in the playlist. The actual implementation called depends on the specific file type, demonstrating polymorphism:
This example shows how polymorphism allows the application to treat different audio file types uniformly through a common interface (AudioFile) while executing the appropriate play() method for each specific file type.
Aspect | Base Class | Superclass |
---|---|---|
Definition | The class from which other classes inherit. | The class from which other classes inherit. |
Usage | Commonly used in C++ terminology. | Commonly used in Java terminology. |
Synonyms | Parent class, superclass. | Parent class, base class. |
Hierarchy | At the top or intermediate level of inheritance. | At the top or intermediate level of inheritance |
Purpose | Provides common attributes and methods. | Provides common attributes and methods. |
Inheritance | Other classes derive from it. | Other classes extend from it. |
Data abstraction, the most basic form of abstraction in Object-Oriented Programming, involves manipulating complex objects where the underlying data structure or characteristics remain hidden.
There are three main levels of data abstraction in OOP:
There are three main types of variables in Object-Oriented Programming:
Yes, it's possible to overload a constructor.
In Java, you can't truly overload the main() method in the sense of having multiple main() methods that the JVM will recognize as entry points for your program. However, you can have multiple methods named main() with different parameter lists within the same class. The JVM will only use the standard main(String[] args) as the entry point.
Here's an example to understand this:
public class MainOverloadExample {
// The actual entry point recognized by JVM
public static void main(String[] args) {
System.out.println("Main method called with String[] args");
// Calling other "main" methods
main();
main(5);
main("Hello");
}
// Overloaded main methods (not entry points)
public static void main() {
System.out.println("Main method with no arguments");
}
public static void main(int number) {
System.out.println("Main method with int argument: " + number);
}
public static void main(String str) {
System.out.println("Main method with String argument: " + str);
}
}
Important points to note:
In Java, there is no explicit copy constructor like in C++. Instead, Java provides a default implementation of object copying through the assignment operator (=) and the constructor that takes an object of the same class as a parameter.
When you create a new object by assigning an existing object to it, Java performs a shallow copy by default. A shallow copy creates a new object and copies the reference values of the instance variables from the original object to the new object. This means that both objects will share the same reference to mutable objects (objects that can be modified after creation, such as arrays or other custom objects).
Here's an example to illustrate object copying in Java:
To create a copy constructor, start by defining a constructor that accepts an object of the same type as its parameter:
public class WebPage {
private String url;
private int loadTime;
public WebPage(WebPage webPage) {
}
}
Afterward, each field of the input object is copied into the new instance:
public class WebPage {
private String url;
private int loadTime;
public WebPage(WebPage webPage) {
this.url = webPage.url;
this.loadTime = webPage.loadTime;
}
}
What we have here is a shallow copy, which is suitable because all our fields—such as String and int—are either primitive types or immutable types.
If the Java class contains mutable fields, an alternative approach in its copy constructor is to perform a deep copy. This ensures that the newly created object is independent of the original one by creating distinct copies of each mutable object:
public class WebPage {
private String url;
private int loadTime;
private Map<String, String> pageElements;
public WebPage(WebPage webPage) {
this.url = webPage.url;
this.loadTime = webPage.loadTime;
this.pageElements = new HashMap<>(webPage.pageElements);
}
}
In Java, the clone method allows us to create an object from an existing object, but the copy constructor offers several advantages:
When a variable is declared static, a single class-level copy is created and shared among all objects. This makes static variables effectively global variables shared across all class instances.
Some important points about static variables are:
When the static keyword is used, methods can be created that do not require any class instances to exist. These are known as static methods.
Syntax:
[Access_modifier] static [return_type] methodName([parameters]) {
// Method body
}
Here are some of the restrictions on Java static methods:
It is not possible to invoke a function without constructing an instance of its class, as there is no object of a class when the JVM starts. The main() function is declared static so that the class can be loaded by JVM into the main memory. This design allows the Java runtime to begin execution without instantiating any objects.
No, static methods cannot be overridden because method overriding is implemented through dynamic binding during runtime, whereas static methods are bound through static binding during compile time. Thus, we cannot override static methods. Often asked, this OOPs interview question is common.
When we use the static keyword with a block of code, it is referred to as a static block. Unlike C++, Java supports a special static block (also known as a static clause) for the static initialization of a class. This code is executed only once when the class is first loaded into memory.
Here's an example:
public class MyClass {
private static int counter;
private static final double PI;
static {
counter = 0;
PI = calculatePi(); // Assume calculatePi() is a method that computes the value of pi
System.out.println("Static block executed");
}
// Rest of the class...
}
In this example, the Static block initializes the counter variable to 0 and the PI constant with the value computed by the calculatePi() method. The message Static block executed will be printed when the MyClass is loaded into memory.
Yes, a Java program can be executed without a main() method by using a static block.
The removal of the static modifier from the main() method would result in the following problems:
This is one of the most commonly asked OOPs interview questions. The following are the differences between static and instance methods:
The this keyword in Java is a reference variable that points to the current object within instance methods or constructors. It's used to distinguish between instance variables and parameters, call methods or constructors of the current class, and pass the current object as an argument.
The this keyword has several important uses:
In Java, the this keyword is a reference variable that refers to the current object instance. However, you cannot assign a new value to this keyword. This restriction is in place because this keyword is a final reference that always points to the current object, and allowing it to be reassigned could lead to significant confusion and errors in the code.
In Java, you cannot use this keyword to access static members. The this keyword refers to the current object instance, whereas static members are class-level entities and not tied to any particular instance. Therefore, using this in a static context is not allowed.
Constructor chaining using this keyword is a technique where one constructor calls another in the same class. Here's how it works:
Let's illustrate this with an example:
This example shows how constructor chaining is done using this keyword:
This is a standard OOPs interview question. The superclass for all classes in Java is the Object class.
Java doesn't support multiple inheritance of classes to avoid the "diamond problem" or "deadly diamond of death." This problem happens when a class inherits from two classes that have a common ancestor, leading to potential ambiguity and complexity.
In this scenario, if B and C both override a method from A, which version should D inherit?
This ambiguity can lead to:
The super keyword in Java is a reference variable that points to the immediate parent class object.
Constructor chaining using the super keyword can be done to call a constructor in the superclass from a subclass.
Here's how it works:
Let's understand this with an example:
// Parent class
class Vehicle {
protected String brand;
protected String model;
public Vehicle() {
this("Unknown", "Unknown");
}
public Vehicle(String brand) {
this(brand, "Unknown");
}
public Vehicle(String brand, String model) {
this.brand = brand;
this.model = model;
}
public void displayInfo() {
System.out.println("Brand: " + brand + ", Model: " + model);
}
}
// Child class
class Car extends Vehicle {
private int numDoors;
public Car() {
super(); // Calls Vehicle()
this.numDoors = 4;
}
public Car(String brand) {
super(brand); // Calls Vehicle(String)
this.numDoors = 4;
}
public Car(String brand, String model) {
super(brand, model); // Calls Vehicle(String, String)
this.numDoors = 4;
}
public Car(String brand, String model, int numDoors) {
super(brand, model); // Calls Vehicle(String, String)
this.numDoors = numDoors;
}
@Override
public void displayInfo() {
super.displayInfo(); // Calls Vehicle's displayInfo()
System.out.println("Number of doors: " + numDoors);
}
}
public class Main {
public static void main(String[] args) {
Car car1 = new Car();
Car car2 = new Car("Toyota");
Car car3 = new Car("Honda", "Civic");
Car car4 = new Car("Ford", "Mustang", 2);
car1.displayInfo();
car2.displayInfo();
car3.displayInfo();
car4.displayInfo();
}
}
In this example:
The super keyword is used for:
Following are the differences between this and super keywords:
Aspect | this Keyword | super Keyword |
---|---|---|
Purpose | Refers to the current instance of the class. | Refers to the immediate parent class instance. |
Usage in Constructors | Calls another constructor in the same class. | Calls a constructor in the immediate parent class. |
Accessing Members | Accesses members of the current class. | Accesses members of the parent class. |
Method Invocation | Invokes current class methods. | Invokes overridden methods of the parent class. |
Syntax for Constructor Call | this() or this(parameters) | super() or super(parameters) |
Position in Constructor | Must be the first statement if used. | Must be the first statement if used. |
Applicable to | Instance methods and constructors. | Instance methods, constructors, and instance variables. |
Use with Static Members | Cannot be used with static members. | Cannot be used with static members. |
Implicit Use | Compiler adds this implicitly when accessing instance members. | Compiler doesn't add super implicitly (except default for the constructor call). |
Overriding | Not applicable | Used to call the overridden method of the parent class |
Scope | Limited to the current class. | Extends to the immediate parent class. |
You cannot use this() and super() together in the same constructor.
Object cloning is the process of creating an exact copy of an object. The clone() method of object class is used to clone an object. The clone() method provided by the object class in Java is utilized for this cloning process.
This is one of the most commonly asked OOPs interview questions. Method overloading is not possible by changing only the return type in Java for the following reasons:
When resolving overloaded methods in Java, if an exact match isn't found, the compiler first promotes lower data type arguments to higher ones. It checks for a matching method after each promotion. If a match is found, that method is used.
If not, the compiler continues promoting until all possibilities are exhausted. If no match is found after all promotions, a compile-time error occurs. This process is known as automatic type promotion in method overloading.
The promotion follows a hierarchy:
byte → short → int → long → float → double
char → int
Let’s take a practical example of programs based on the automatic type promotion concept:
public class TypePromotionExample {
public void display(int a) {
System.out.println("int: " + a);
}
public void display(double a) {
System.out.println("double: " + a);
}
public static void main(String[] args) {
TypePromotionExample obj = new TypePromotionExample();
byte b = 25;
obj.display(b); // Promotes byte to int
short s = 30;
obj.display(s); // Promotes short to int
char c = 'A';
obj.display(c); // Promotes char to int
float f = 3.14f;
obj.display(f); // Promotes float to double
}
}
In this example:
Yes, we can adjust the scope of the overridden method in the subclass. It's important to note that while increasing its accessibility, we cannot decrease it.
The instanceof operator is a binary operator that checks whether an object belongs to a specific type. It returns either true or false, making it a type comparison operator as it matches the instance against the type. The basic syntax of the instanceof operator is:
The basic syntax of the instanceof operator is:
(object) instanceof (type)
Encapsulation in Java, a fundamental concept in real-time programming, provides several advantages:
In Java, exceptions are categorized into three main types:
Exception handling is a mechanism designed to manage runtime errors, including ClassNotFoundException, IOException, SQLException, RemoteException, and others.
In Java's exception hierarchy, the Throwable class occupies the highest position, succeeded by its subclasses Error and Exception. The following shows the hierarchy of Java Exception classes.
It's important to differentiate between Error and Exception because they represent fundamentally different categories of issues, each requiring specific handling approaches.
An exception is an unexpected event in a program that can be managed and recovered from within the program itself. In contrast, an error represents a more severe condition that typically cannot be handled within the program as it may cause damage to the system's architecture or environment.
Following are the key differences between checked and unchecked exceptions:
Aspect | Checked Exceptions | Unchecked Exceptions |
---|---|---|
Compile-Time Checking | Must be caught or declared | Not required to be caught or declared |
Class Hierarchy | Subclasses of exception (excluding RuntimeException ) | Subclasses of RuntimeException |
Error Handling | For recoverable errors | For programming errors |
When to Use | Anticipated, recoverable conditions | Unexpected failures |
Examples | IOException, SQLException | NullPointerException, ArithmeticException |
Method Signatures | Must be declared in a throws clause. | No need to declare. |
Propagation | Must be explicitly propagated. | Automatically propagate. |
Performance Impact | Can have some impact. | Generally, it has less impact. |
Handling Enforcement | Enforced by the compiler. | Not enforced by the compiler. |
The finally block in programming, found commonly in languages such as Java and C#, is a segment of code that runs regardless of whether an exception is thrown or not.
Typically used with a try-catch block, the finally block ensures critical cleanup operations, like closing files or database connections, are executed.
Syntax for a finally block:
try {
// Code that might throw an exception
} catch (ExceptionType1 e1) {
// Handle exception of ExceptionType1
} catch (ExceptionType2 e2) {
// Handle exception of ExceptionType2
} finally {
// Code that will always execute, whether an exception occurred or not
}
There are many differences between throw and throws keywords. A list of differences between them is given below:
Aspect | throw | throws |
---|---|---|
Purpose | Used to explicitly throw an exception. | Used to declare that a method might throw exceptions. |
Usage Location | Used inside a method. | Used in the method signature. |
When It's Used | At runtime, when a specific condition is met. | At compile time, to inform the caller about possible exceptions. |
Number of Exceptions | Throws a single exception at a time. | Can declare multiple exceptions. |
Exception Creation | Creates and throws an actual exception object. | Does not create exceptions, it just declares possibility. |
Execution | Immediately transfers control to the exception handler. | Does not immediately affect program flow. |
Handling Requirement | Not required to be handled or declared. | Checked exceptions must be handled or re-declared. |
Applicable to | Both checked and unchecked exceptions. | Typically used with checked exceptions. |
Example | throw new IOException("File not found"); | public void readFile() throws IOException, FileNotFoundException |
Exception propagation refers to the process of forwarding exceptions from a called method to its caller. If such an exception isn't handled by the caller, the called method and the caller terminate execution.
Garbage collection is a computer programming term that describes identifying and deleting objects no longer referenced by other objects.
In simple terms, garbage collection refers to discarding objects no longer needed or referenced by any other parts of the program. It's an essential aspect of how JavaScript handles memory allocation.
Java provides four types of garbage collectors that can be chosen based on requirements:
The main disadvantage of garbage collection is that it pauses all active threads during the memory recovery phase. Garbage collection algorithms can take significant time, ranging from seconds to minutes, to execute. This extended duration makes it challenging to schedule garbage collection routines predictably.
There are several ways an object can become unreferenced:
Employee e = new Employee();
e = null; // The Employee object is now unreferenced
Employee e1 = new Employee();
Employee e2 = new Employee();
e1 = e2; // The first Employee object is now unreferenced
new Employee(); // This Employee object is immediately unreferenced
void createEmployee() {
Employee e = new Employee();
} // 'e' goes out of scope, potentially dereferencing the object
List<Employee> employees = new ArrayList<>();
employees.add(new Employee());
employees.remove(0); // This Employee object may now be unreferenced
Each of these methods can result in objects becoming unreachable from the root set, making them eligible for garbage collection. The exact timing of when these objects are collected depends on the JVM's garbage collection implementation and strategy.
The finalize() method is defined in the object class, which can be overridden by subclasses. The garbage collector calls the finalize() method before an object is collected. This method can perform essential cleanup tasks before destroying the object, such as releasing resources or detaching event listeners.
Java uses the keywords final, finally, and finalize in its exception handling mechanisms, each having its specific role. Below is a list of the differences between them:
Aspect | final | finally | finalize |
---|---|---|---|
Type | keyword | block | method |
Purpose | To create constants, prevent inheritance/overriding. | To execute code regardless of exception occurrence. | To perform cleanup operations before the object is garbage collected. |
Usage | Can be applied to variables, methods, classes. | Used with try-catch blocks. | Defined in the object class, can be overridden. |
When it Executes | Compile-time (for variables), runtime (for methods/classes). | Always executes after try-catch blocks. | Called by the garbage collector before reclaiming the object's memory. |
Can be Overridden | No (when applied to methods/classes). | N/A | Yes |
Execution Guarantee | N/A | Guaranteed to execute (except in specific cases). | Not guaranteed to be called. |
Related to | Variables, methods, classes | Exception handling | Object life cycle |
Commonly Used for | Constants, immutable objects, preventing inheritance. | Resource cleanup (closing files, connections). | Releasing resources that weren't cleaned up by try-finally. |
Now that you've familiarized yourself with some of the most commonly asked OOPs interview questions and answers, it's essential to delve deeper into each of these concepts. This preparation will be instrumental in positioning yourself for success in OOPs-focused Java development roles.
Now that you've familiarized yourself with some of the most commonly asked OOPs interview questions and answers, it's essential to delve deeper into each of these concepts. This preparation will be instrumental in positioning yourself for success in OOPs-focused Java development roles.
Did you find this page helpful?
Try LambdaTest Now !!
Get 100 minutes of automation test minutes FREE!!