JAVA OOP
JAVA OOP
4 pillars of OOP:
1. Encapsulation
2. Abstraction
3. Inheritance
4. Polymorphism
1. Class:
2. Object:
3. Encapsulation:
This principle involves bundling data (properties) and the methods that
operate on the data into a single unit (class). It also involves hiding the
internal details of how data is stored and accessed, exposing only
necessary functionality.
4. Abstraction:
Intro to OOP 1
Example: Using interfaces or abstract classes to hide implementation
details.
5. Inheritance:
6. Polymorphism:
Benefits of OOP:
Modularity: The code is organized into classes and objects, making it easier
to maintain and extend.
Scalability: It's easier to scale applications by adding new classes and objects
without affecting the existing ones.
Intro to OOP 2
Classes and Objects
1. Object:
Example: A Human object has properties like name , age , gender , and
behaviors like canRun() , canEat() .
2. Class:
Example:
class Pen {
// Properties (variables)
String color = "blue";
float tip = 0.7f;
// Behavior (method)
void displayColor() {
System.out.println("The color of the pen is " + color);
}
}
You can create an object (instance) of a class using the new keyword.
Example:
Key Points:
Properties are defined by variables inside a class.
The class serves as a blueprint, while objects are the actual instances.
Important Questions
1. Can you explain what happens when an object is created from a class, step
by step?
Answer:
2. Object Creation: Using the new keyword, a new instance of the class
is created.
2. What error occurs when you have a public class defined within another
class file in Java, and how can you fix it?
Error:
Reason:
In Java, each public class must be in a file with the same name as the class. A
class named Pen must be in a file called Pen.java . You can only have one public
class per file.
Conclusion:
Java requires the file name to match the public class name. If you don't match
it, you'll get a compilation error. You can either rename the file or remove public
to avoid the error.
Can you use other access modifiers (like protected , private , or default ) for top-
level classes?
No, you can only use public or no modifier (package-private) for top-level
classes. Using protected or private will cause an error.
1. No return type: Constructors don't have a return type, not even void .
2. Same name as the class: The constructor's name must be the same as the
class name.
Types of Constructors:
2. Parameterized Constructor:
Constructors 1
public class MyClass {
private int value;
// Parameterized constructor
MyClass(int value) {
this.value = value;
System.out.println("Object created with value: " + value);
}
}
Constructor Overloading:
Java allows having more than one constructor in a class, each with a different
number or type of parameters. This is known as constructor overloading and
lets you create objects in different ways.
// Default constructor
MyClass() {
this.value = 0;
}
// Parameterized constructor
MyClass(int value) {
this.value = value;
}
}
Important Questions
1. Can a class have no constructor? If yes, what happens in that case?
Constructors 2
Yes, a class can have no constructor. In that case, Java provides a default
constructor that initializes the object with default values (e.g., 0 for
integers, null for objects, false for boolean).
class MyClass {
int num;
String name;
}
If you don't initialize an object's properties explicitly, Java will assign them
default values (e.g., 0 for int , null for reference types, false for boolean ).
class Singleton {
private static Singleton instance;
Constructors 3
if (instance == null) {
instance = new Singleton();
}
return instance;
}
}
class Parent {
Parent() {
System.out.println("Parent constructor called");
}
}
No, constructors cannot be invoked like normal methods. They are invoked
implicitly when an object is created using the new keyword. You cannot
explicitly call a constructor from another part of the code.
Constructors 4
Constructors are instance-specific, while static methods are class-
specific.
Constructors 5
new Keyword
The new keyword in Java is used to create new objects and allocate memory for
them. It is crucial for object-oriented programming in Java because it allows you
to instantiate classes and allocate memory for new instances of objects.
1. Object Creation:
The primary use of the new keyword is to create an instance (or object) of
a class. When you create an object using new , memory is allocated in the
heap for that object.
Syntax:
2. Memory Allocation:
When you use new , Java allocates memory for the object in the heap and
initializes its instance variables (fields) to default values (if not initialized).
3. Constructor Invocation:
The new keyword also calls the constructor of the class to initialize the
object. If no constructor is explicitly defined, Java calls the default
constructor (if available).
4. Garbage Collection:
Example:
new Keyword 1
class Pen {
String color;
float tip;
// Constructor
Pen(String color, float tip) {
this.color = color;
this.tip = tip;
}
Here, Pen p1 = new Pen("blue", 0.7f); creates an object of the Pen class, calling the
constructor with the arguments "blue" and 0.7f .
Conclusion:
The new keyword in Java is used to create objects and allocate memory for
them.
new Keyword 2
Important Questions
1. What happens if you create an object inside a method without using the new
keyword?
If you try to create an object without using the new keyword, you will get a
compile-time error because Java requires the new keyword to allocate
memory for the object and initialize it.
2. What happens when the new keyword is used to create an object in Java?
new Keyword 3
this Keyword
The this keyword is used to refer to the current object. It helps to distinguish
between instance variables (class attributes) and parameters or local variables
that may have the same name.
public void setId(int id) { //'id' is both a parameter and a class attribute
id = id;
// Java doesn't know which 'id' to assign (class attribute or parameter)
}
}
Problem:
It's helpful when you need to differentiate between a class's instance variable
and a parameter with the same name.
Example:
this Keyword 1
public void setId(int id) {
// Here, 'id' refers to the parameter, and 'this.id' refers to the instance var
iable
this.id = id; // 'this.id' refers to the instance variable
}
}
In this example, this.id refers to the instance variable id , while the method
parameter id is used to initialize it. Without this , Java would assume you're
referring to the method parameter.
1. Object Creation:
Employee obj = new Employee(); creates an instance of the Employee class. Let's say
this instance is stored in memory with a reference like obj .
This means the setId method is now aware of the specific object ( obj )
it is supposed to modify.
3. Method Execution:
Here, obj1 points to the same memory location as obj . The line obj1.id = id; is
equivalent to this.id = id; .
this Keyword 2
4. Why this is Used:
The this keyword acts as a shorthand, allowing the developer to write this.id
Important Questions
1. Can this be used in a static context?
No, this cannot be used in a static context (e.g., static methods or static
blocks). The this keyword refers to the current instance, but static
members belong to the class, not to any specific instance.
class Example {
void display() {
print(this); // Passes the current object
}
void print(Example obj) {
System.out.println("Printing object");
}
}
class Test {
int x = 10;
void display() {
int x = 20;
System.out.println(x); // Local variable x
System.out.println(this.x); // Instance variable x
}
public static void main(String[] args) {
this Keyword 3
Test obj = new Test();
obj.display();
}
}
Answer:
20
10
Yes, this can be used to return the current object from a method. This is
often used in method chaining. For example:
class Example {
int x;
Example setX(int x) {
this.x = x;
return this; // Returns the current object
}
}
class Test {
Test() {
this(10);
System.out.println("Default constructor");
}
Test(int x) {
System.out.println("Parameterized constructor: " + x);
}
this Keyword 4
public static void main(String[] args) {
Test obj = new Test();
}
}
Answer:
Parameterized constructor: 10
Default constructor
this Keyword 5
Encapsulation
Encapsulation is a fundamental concept in Object-Oriented Programming (OOP). It
is about hiding the internal details of a class and only exposing what is
necessary. It combines data (variables) and behavior (methods) into a single unit
(class).
Key Features:
1. Data Hiding: The class variables (data) are declared as private , restricting
direct access from outside the class.
2. Access Through Methods: The variables are accessed and modified using
public getter and setter methods.
class Employee {
// Private variables (data hiding)
private String name;
private int id;
Encapsulation 1
return name;
}
What Happens:
1. The variables id and name are private and cannot be accessed directly from
outside the Employee class.
3. The getId and getName methods allow controlled access to these variables.
Encapsulation 2
Control: Provides control over data modification.
Flexibility: You can change the implementation without affecting the external
code.
Key Takeaways:
Encapsulation ensures data integrity and security, which is crucial for large
and complex systems.
Access Modifiers
Access modifiers are a key part of implementing encapsulation in Java. They
help control the visibility and accessibility of class members (variables and
methods) and play a crucial role in bundling data and methods while hiding
implementation details.
Subclass
Within Outside
Access Modifier Within Class (outside
Package Package
package)
Encapsulation 3
Polymorphism
Polymorphism is a core concept in Object-Oriented Programming (OOP) that
allows methods or objects to behave differently based on the context. In simple
terms, polymorphism means "many forms."
A person can act as a teacher in school and a parent at home, but they are still
the same person.
Decided at runtime.
When multiple methods have the same name but differ in:
Number of parameters,
Type of parameters, or
Order of parameters.
Polymorphism 1
class MathUtils {
// Method with two integer parameters
int add(int a, int b) {
return a + b;
}
Explanation
At Compile Time: The Java compiler decides which add method to call based
on the number and type of arguments passed.
Polymorphism 2
Why It’s Useful: Overloading allows flexibility by using the same method name
for similar operations.
When a child class provides a specific implementation for a method that is already
defined in its parent class, it is called method overriding.
Rules for Method Overriding
1. The method in the child class must have the same name, return type, and
parameters as the method in the parent class.
class Animal {
void makeSound() {
System.out.println("Animals make sounds");
}
}
Polymorphism 3
}
Explanation
2. Dynamic Binding: At runtime, the JVM decides to call the method based on
the actual object (e.g., Dog or Cat ) that myAnimal refers to.
Polymorphism 4
Important Questions
1. Can we overload methods by changing only the return type?
Answer:
No, method overloading is not possible by only changing the return type.
The method signature must differ in parameters (number, type, or order).
Answer:
Answer:
The code will still compile and run, but if the method signature in the
subclass is incorrect (e.g., wrong parameter or return type), it will not
override the method from the parent class, leading to unexpected
behavior.
Answer:
Answer:
Polymorphism 5
Covariant return types allow a subclass to override a method and return a
more specific type (subtype) than the method in the parent class.
Example:
class Parent {
Parent display() {
System.out.println("Parent display");
return this;
}
}
class Child extends Parent {
@Override
Child display() {
System.out.println("Child display");
return this;
}
}
public class Test {
public static void main(String[] args) {
Parent obj = new Child();
obj.display(); // Child display
}
}
Answer:
Polymorphism 6
class Parent {
void display() {
System.out.println("Parent display");
}
}
Answer:
It will print Child display . At runtime, the Child 's display() method is called
because the actual object is of type Child .
Polymorphism 7
Inheritance
Inheritance allows one class (child class) to acquire properties and methods from
another class (parent class). It promotes code reusability, scalability, and
improves readability by preventing redundancy.
The class that inherits properties and methods from the superclass.
Syntax of Inheritance
class SuperClass {
// properties and methods of the superclass
}
1. Single-Level Inheritance
A subclass inherits from one parent class.
Example:
Inheritance 1
class Animal {
void eat() {
System.out.println("This animal eats food.");
}
}
Output:
2. Multi-Level Inheritance
A class inherits from another class, which itself is a subclass of another.
Example:
Inheritance 2
class Animal {
void eat() {
System.out.println("This animal eats food.");
}
}
Output:
Inheritance 3
3. Hierarchical Inheritance
Multiple subclasses inherit from a single parent class.
Example:
class Animal {
void eat() {
System.out.println("Eats food.");
}
}
Inheritance 4
Output:
Eats food.
The dog barks.
This animal eats food.
The cat meows.
4. Hybrid Inheritance
In languages like Java, hybrid inheritance can also be achieved by combining
different types of inheritance like single-level, multi-level, and hierarchical
inheritance.
class Animal {
void eat() {
System.out.println("Eats food.");
}
}
Inheritance 5
class PetDog extends Dog {
void play() {
System.out.println("The dog plays.");
}
}
Output:
Eats food.
The dog barks.
The dog plays.
This animal eats food.
The cat meows.
Explanation:
In this example, we're combining multi-level inheritance (Dog → PetDog) and
hierarchical inheritance (Dog and Cat both inherit from Animal). Even without
interfaces, this demonstrates a "hybrid" inheritance approach by utilizing multiple
inheritance mechanisms in one program.
5. Multiple Inheritance
Inheritance 6
Java does not support multiple inheritance with classes.
Multiple inheritance occurs when a class tries to inherit from two or more
classes, leading to ambiguity.
Example of Ambiguity:
class A {
void show() {
System.out.println("Method from Class A");
}
}
class B {
void show() {
System.out.println("Method from Class B");
}
}
If both parent classes ( A and B ) have a method with the same name,
Java cannot determine which method to inherit.
A has show() and B also has show() now which show() needs to be
called by the inherited class ?
Advantages of Inheritance
Inheritance 7
1. Code Reusability:
Methods and properties of the parent class can be reused in the child
class without rewriting them.
2. Extensibility:
3. Improved Maintainability:
1. Access Modifiers:
Public and protected members are inherited. Private members are not
directly inherited but can be accessed via public or protected methods.
Example:
class Animal {
private void secret() {
System.out.println("This is a secret!");
}
Inheritance 8
2. Constructors are not inherited.
Example:
Output:
class Animal {
Animal() {
System.out.println("Animal constructor called");
}
}
3. Overriding Methods:
A child class can override parent class methods to provide its specific
implementation.
Example:
Inheritance 9
class Animal {
void sound() {
System.out.println("Animals make sounds");
}
}
Disadvantages of Inheritance
1. Tight Coupling:
The child class depends on the parent class; changes in the parent class
can affect subclasses.
2. Increase in Complexity:
Important Questions
1. Can we inherit private members of a class?
Inheritance 10
Answer:
No, private members of a class cannot be directly inherited. They are not
accessible outside the class, including in subclasses. However, you can
access them indirectly through public or protected methods in the parent
class.
Answer:
Static methods belong to the class, not instances, so they are not
overridden. Instead, they can be hidden.
Answer:
4. What is the diamond problem in Java, and how does Java solve it?
Answer:
5. What happens if two parent classes have methods with the same signature,
and a subclass inherits both?
Answer:
Inheritance 11
Java does not allow multiple inheritance with classes, so if you attempt
to create such a scenario, it will lead to a compilation error. Java resolves
this issue by supporting multiple inheritance only through interfaces.
If both interfaces have the same method signature, the subclass must override
the method and provide an implementation.
Example with interfaces:
interface A {
void display();
}
interface B {
void display();
}
class C implements A, B {
@Override
public void display() {
System.out.println("Method from class C");
}
}
Answer:
interface.
Example:
class Animal {}
class Dog extends Animal {}
Inheritance 12
Animal a = new Dog();
if (a instanceof Dog) {
System.out.println("a is an instance of Dog");
}
Answer:
Inheritance 13
static Keyword
The static keyword in Java is used to share variables or methods among all
instances (objects) of a class. This means, instead of each object having its own
copy of the variable or method, the class itself holds one shared version of it. This
is especially useful for memory management because static variables and
methods are loaded into memory only once, regardless of how many objects are
created.
3. Static Blocks
class Mobile {
static String brand; // Static variable
static int price; // Static variable
}
static Keyword 1
Mobile obj2 = new Mobile(); // Second object of Mobile
Explanation:
Both obj1 and obj2 share the same static variables brand and price because
static variables belong to the class itself, not the individual objects.
When obj1 assigns "Apple" to brand , the same brand is reflected in obj2 (since
they share it).
static Keyword 2
Key points about static method:
You can access static variables directly using the class name, without
creating an instance.
Shared among all objects of the class, and only one copy exists in memory.
Example:
class Mobile {
static String brand = "Samsung"; // Static variable
// Static method
public static void showBrand() {
System.out.println("Brand: " + brand); // Accessing static variable
static Keyword 3
}
}
Explanation:
The showBrand() method is static, so it can be called directly using the class
name Mobile.showBrand() without creating an object.
Static methods cannot use this or super because these keywords refer to the
current object or parent class, and static methods are not tied to any instance.
Static methods cannot be overridden because they belong to the class, not
instances. If a subclass defines a static method with the same signature, it is
method hiding, not overriding.
Static methods are often used for utility or helper functionality, such as Math
methods:
Math.max(10, 20);
Math.sqrt(25);
3. Static Block
A static block is used to initialize static variables when the class is first loaded. It
is executed only once, when the class is loaded into memory.
Example:
static Keyword 4
class Example {
static int number; // Static variable
Explanation:
The static block runs once when the class is loaded, even before any objects
are created.
Example:
class OuterClass {
static String outerVariable = "Outer Class";// Static variable in outer class
static Keyword 5
// Accessing static variable of outer class
}
}
}
Explanation:
Important Questions
1. Can we use static variables in non-static methods ?
Yes, static variables can be used in both static and non-static methods. This is
because static variables belong to the class itself, not any specific instance. So,
they are accessible from both static and non-static methods.
You cannot use super (to refer to the superclass) or this (to refer to the current
object) inside a static method because static methods are not associated with any
specific object.
static Keyword 6
No, non-static variables cannot be accessed directly in a static method. This is
because non-static variables belong to individual objects, whereas static methods
are associated with the class itself. Since a static method doesn't know which
object (or instance) it's working with, it can't directly access instance variables
(non-static variables).
class Mobile {
String brand; // Non-static variable
int price; // Non-static variable
brand and price are instance variables. Each object of Mobile has its own value
for these variables.
The static method show() doesn't know which object's brand or price to print
because it is not associated with any object. It belongs to the class, and thus
can't access instance variables directly.
static Keyword 7
4. How to Access Non-Static Variables in a Static Method ?
Although you can't directly access non-static variables in a static method, you can
pass an object as a parameter to the static method. Then, you can access the
non-static variables through that object.
Example:
class Mobile {
String brand; // Non-static variable
int price; // Non-static variable
Explanation:
We can access the non-static variables ( brand and price ) of that object inside
the static method.
static Keyword 8
Output:
Apple: 1500
Samsung: 2500
3. However, the program's execution begins with main() , and if execution hasn’t
started yet, there is no way to create an object of the Hello class.
1. The JVM can call main directly without creating an object of the class.
So, the main method must be static to allow the JVM to execute it as the entry
point without requiring an object.
static Keyword 9
Constructor → Runs Every Time:
A constructor runs whenever a new object is created. If you initialize a static
variable in a constructor, it will reset the variable each time an object is
created, overwriting the previous value.
Static variables belong to the class, not objects. Using a constructor for static
variables leads to redundant initialization.
1. Executes Once:
A static block runs only once, when the class is loaded, making it efficient
for static variable initialization.
2. Avoids Overwriting:
Ensures static variables are initialized just once, regardless of the number
of objects created.
Example
With Constructor
class Example {
static int num;
Example() { num = 10; } // Runs every object creation
}
class Example {
static int num;
static { num = 10; } // Runs only once
}
static Keyword 10
super Keyword
The super keyword is used to refer to the parent class in Java.
If the parent class has a parameterized constructor, you must explicitly call it
using super(parameters) .
class A {
A() { System.out.println("In A"); }
A(int n) { System.out.println("In A-parameterized"); }
}
class B extends A {
B() {
super Keyword 1
//super(); // Calls parent’s default constructor(no need to use super())
System.out.println("In B");
}
B(int n) {
super(n); // Calls parent’s parameterized constructor
System.out.println("In B-parameterized");
}
}
Output:
In A
In B
In A-parameterized
In B-parameterized
class A {
int a = 10;
void display() { System.out.println("Display in A"); }
}
super Keyword 2
class B extends A {
int a = 20;
void display() {
super.display(); // Calls parent’s display method
System.out.println("Super a: " + super.a); // Access parent’s variable
System.out.println("Child a: " + this.a); // Access child’s variable
}
}
Output:
Display in A
Super a: 10
Child a: 20
Example:
class A {
A() { System.out.println("In A"); }
}
class B extends A {
super Keyword 3
B() { System.out.println("In B"); }
B(int n) {
this(); // Calls the default constructor in the same class
System.out.println("In B-int");
}
}
Important Questions
1. Can super be used inside a static method?
No, super cannot be used inside a static method because super is linked to an
instance, and static methods belong to the class, not an instance.
2. Can you call both super() and this() in the same constructor?
No, because both must be the first statement, and Java does not allow two first
statements in a constructor.
3. Can a subclass call a private method of the parent class using super ?
No, super cannot access private methods of the parent class because private
methods are not inherited.
4. If a parent class and a child class have the same method name, how do you
call the parent’s method from the child class?
Use super.methodName(); to call the parent class's method inside the child class.
Yes, but only as the first statement to call the parent class constructor.
super Keyword 4
6. If a parent class has multiple constructors, how does the child class choose
which one to call?
The child class must explicitly call the required constructor using super(arguments); .
7. In Java, why do we need the super keyword if we can access parent class
properties through inheritance?
While inheritance allows a subclass to access the properties and methods of its
parent class, the super keyword is necessary for specific scenarios where explicit
interaction with the parent class is required. Here's why the super keyword is
essential:
class Parent {
Parent(int x) {
System.out.println("Parent constructor: " + x);
}
}
Without super , you wouldn't be able to invoke the parent class's constructor
explicitly.
super Keyword 5
If a subclass defines a field or method with the same name as one in the
parent class, the subclass's member shadows or overrides the parent's
member. The super keyword is used to access the parent class's version of the
member.
class Parent {
int x = 10;
}
void print() {
System.out.println("Child x: " + x); // Accesses Child's x
System.out.println("Parent x: " + super.x); // Accesses Parent's x
}
}
Without super , you wouldn't be able to access the parent class's x if it's
shadowed by the subclass's x .
If a subclass overrides a method from the parent class, super can be used to
call the parent class's overridden method.
class Parent {
void display() {
System.out.println("Parent display");
}
}
super Keyword 6
}
}
Without super , you wouldn't be able to invoke the parent class's overridden
method.
In Java, super() must be the first line of a constructor because the parent class's
constructor needs to be called before the subclass's constructor can execute.
This ensures that the parent class is properly initialized before the subclass
begins its own initialization.
9. What happens if we try to initialize super() in any other line besides the first
line of a constructor?
If you try to call super() in any line other than the first line of a constructor, the Java
compiler will throw a compile-time error. This is because Java enforces strict
rules about constructor chaining to ensure proper initialization of objects.
super Keyword 7
final Keyword
The final keyword is used to define entities (variables, methods, or classes) that
cannot be changed, overridden, or extended. Here's how it works:
1. Final Variable
A variable declared as final can be assigned only once.
Example:
2. Final Method
A final method cannot be overridden by subclasses.
Example:
class Parent {
final void display() {
System.out.println("Display in Parent");
}
}
3. Final Class
final Keyword 1
A final class cannot be inherited.
Example:
class Child extends Parent { } // Error: Cannot inherit from final class
Feature Description
final Used to declare constants, prevent method overriding, or inheritance.
final Keyword 2
abstract Keyword
The abstract keyword is used to define abstract classes and abstract methods.
1. Abstract Class
An abstract class cannot be instantiated directly, meaning you cannot create
objects of an abstract class.
It may contain both abstract methods (methods without a body) and non-
abstract methods (methods with a body).
Example:
2. Abstract Method
An abstract method is a method without a body. It must be implemented by
subclasses of the abstract class.
Example:
abstract Keyword 1
Example:
abstract Keyword 2
Interfaces
An interface in Java is a reference type, similar to a class, but it can only contain
abstract methods (until Java 8, after which it can contain default and static
methods as well). Interfaces are used to define a contract that classes must
adhere to.
A class implements an interface and must provide implementations for all the
abstract methods declared in the interface.
2. No Constructor
All variables declared inside an interface are implicitly public, static, and
final.
4. Multiple Inheritance
Interfaces 1
Interfaces can also contain static methods. These are similar to static
methods in classes, and they are invoked by the interface name.
Interface Implementation
A class that implements an interface must provide concrete implementations for
all abstract methods declared by the interface.
interface Animal {
void sound();
}
Note: A class must implement all abstract methods from an interface unless
the class is abstract itself.
Functional Interface
Interfaces 2
Functional interfaces can have multiple default or static methods, but they
must have exactly one abstract method.
@FunctionalInterface
interface Calculator {
int add(int a, int b); // Single abstract method
Inheritance of Interfaces
An interface can extend another interface, just like classes inherit from other
classes.
interface Animal {
void sound();
}
Interfaces 3
@Override
public void walk() {
System.out.println("Walks on 4 legs");
}
}
Yes, an interface can extend multiple interfaces, allowing multiple inheritance for
interfaces.
interface Animal {
void sound();
}
interface Mammal {
void walk();
}
interface Animal {
void sound();
}
Interfaces 4
public static void main(String[] args) {
Animal dog = new Animal() {
public void sound() {
System.out.println("Bark");
}
};
dog.sound(); // Output: Bark
}
}
Abstract Class:
Interface:
Important Questions
1. What happens if two interfaces have the same default method signature?
Answer: If two interfaces that a class implements have the same default
method signature, the class must override the method to resolve the conflict.
Java does not know which default method to inherit, so it forces the class to
provide its own implementation.
Interfaces 5
interface A {
default void display() {
System.out.println("Display from A");
}
}
interface B {
default void display() {
System.out.println("Display from B");
}
}
class C implements A, B {
@Override
public void display() {
System.out.println("Display from C");
}
}
Answer: Since Java 9, interfaces can have private methods. These private
methods cannot be accessed outside the interface, but they can be used to
share code between default methods in the interface.
interface A {
private void privateMethod() {
System.out.println("Private method");
}
Interfaces 6
3. What happens if a class implements an interface but does not provide
implementations for all abstract methods?
Answer: No, an interface cannot extend a class. An interface can only extend
other interfaces. However, a class can implement multiple interfaces and
extend one class.
Answer: Yes, an interface can have multiple methods with the same name, but
they must have different parameter lists (overloading). Methods in an interface
can also have the same name as long as they are not conflicting.
interface A {
void display(int x);
void display(String x);
}
Answer: Yes, an interface can have a main method, and it can be executed just
like a class. However, it is not common to define a main method in an interface,
as the interface is typically used to define behavior that will be implemented
by other classes.
interface A {
public static void main(String[] args) {
System.out.println("Main method in interface");
}
}
Interfaces 7
7. What happens in the following code?
interface Main {
class A {
int a = 10;
}
This code demonstrates the use of a main method inside an interface along
with a nested class. Here's what happens:
The Main interface contains a public static void main(String[] args) method,
which serves as the entry point for the program.
2. Nested Class A :
The class A is defined inside the Main interface. This is a nested class
and is implicitly static because it is defined inside an interface.
3. Creating an Instance of A :
Interfaces 8
Main method in interface
10
Classes defined inside an interface are implicitly static and public . They
can be instantiated and used like any other class.
Since the main method is static , you don’t need to create an instance of
the Main interface or provide an implementing class to run the
program.
javac Main.java
java Main
Answer:
Example:
interface Animal {
void makeSound();
}
Interfaces 9
class Dog implements Animal {
public void makeSound() {
System.out.println("Dog barks");
}
}
class Cat implements Animal {
public void makeSound() {
System.out.println("Cat meows");
}
}
public class Test {
public static void main(String[] args) {
Animal animal;
animal = new Dog();
animal.makeSound(); // Dog barks
animal = new Cat();
animal.makeSound(); // Cat meows
}
}
Interfaces 10
Lambda Expressions
Lambda expressions in Java provide a way to express instances of functional
interfaces (interfaces with a single abstract method) in a more concise and
readable way. They enable you to write code that treats functionality as a method
argument or passes behavior as an argument.
Syntax Breakdown
Body: The expression or block of code that defines what the lambda does.
Lambda Expressions 1
(a, b) -> {
int result = a + b;
return result;
}
Here:
The body contains a single line of code, which prints "Hello, World!".
Here:
// A lambda expression that takes two parameters and returns their sum
BiFunction<Integer, Integer, Integer> add = (a, b) -> a + b;
System.out.println(add.apply(5, 3)); // Output: 8
Here:
Lambda Expressions 2
The lambda expression takes two parameters ( a and b ).
Functional Interface
@FunctionalInterface
interface Greet {
void sayHello(String name); // Single abstract method
}
Output:
Hello, Alice
In this example:
The Greet interface is a functional interface because it has only one abstract
method: sayHello .
The lambda expression (name) -> System.out.println("Hello, " + name) is used to provide
the implementation of sayHello .
Lambda Expressions 3
Object class
In Java, all classes implicitly extend the Object class. This means every class you
create automatically inherits methods from Object , which is the root class of the
Java class hierarchy.
1. equals(Object obj)
2. toString()
If you do not override the equals() and toString() methods in your custom class, the
default behavior provided by the Object class will be used.
By default, the equals() method in the Object class checks for reference equality,
meaning it compares if the two object references point to the same memory
location (i.e., the same object in memory). This is not typically useful when
comparing objects based on their contents (like field values).
class Person {
String name;
int age;
Object class 1
}
System.out.println(person1.equals(person2)); // false
}
}
Output:
false
Even though person1 and person2 have the same values ( "Alice" and 25 ), the equals()
method in Object checks for reference equality (whether they point to the same
memory location), not content equality. Therefore, it will return false .
By default, the toString() method in the Object class returns a string representation
of the object, which includes:
The hash code of the object (a unique identifier based on memory address).
class Person {
String name;
int age;
Object class 2
}
}
Output:
Person@15db9742
Here:
1. equals(Object obj)
By default, the equals method checks for reference equality (whether two
references point to the same object in memory). However, this is often
overridden in custom classes to compare object content (the values of
fields).
Object class 3
class Person {
String name;
int age;
System.out.println(person1.equals(person2)); // true
System.out.println(person1.equals(person3)); // false
}
}
Output:
Object class 4
true
false
2. toString()
class Person {
String name;
int age;
Object class 5
Output:
Person[name=Alice, age=25]
Object class 6
Inner Class
An inner class in Java is a class defined within another class. Inner classes are
associated with the instance of the outer class, meaning they can access all
members (including private ones) of the outer class.
1. Nested (Static) Class: A static inner class that belongs to the outer class and
can be accessed without an instance of the outer class.
Inner Class 1
}
}
Output:
class Inner {
void display() {
System.out.println(message);
}
}
Output:
Inner Class 2
A local inner class is defined inside a method or a block. It is local to the scope in
which it is defined and cannot be accessed outside that scope.
Output:
Inner Class 3
public static void main(String[] args) {
Greeting greet = new Greeting() {
@Override
public void sayHello() {
System.out.println("Hello from Anonymous Inner Class!");
}
};
greet.sayHello();
}
}
Output:
outer.display();
Inner Class 4
}
}
Output:
Inner Class 5
Wrapper Class
In Java, wrapper classes are used to convert primitive data types (like int , double ,
char , etc.) into corresponding objects. Each primitive type has a corresponding
short Short
int Integer
long Long
float Float
double Double
char Character
boolean Boolean
Wrapper Class 1
Unboxing: Automatically converting a wrapper class object into its
corresponding primitive type.
Output:
Autoboxed: 10
Unboxed: 20
Wrapper Class 2
Convert numbers or booleans to strings.
3. Value Methods
4. Comparing Values
Integer a = 5, b = 10;
System.out.println(a.compareTo(b)); // Output: -1 (a < b)
Performance Considerations
Memory Usage: Wrapper objects consume more memory than primitive types
because they store additional metadata.
Wrapper Class 3
Boxing/Unboxing Overhead: Frequent boxing/unboxing can impact
performance. For performance-critical applications, prefer primitives.
Wrapper Class 4
Enums
In Java, an enum (short for "enumeration") is a special data type that represents a
fixed set of constants. It is used when you know all possible values for a variable
at compile time. Enums are type-safe, which means they ensure the variable can
only hold one of the predefined constant values.
3. Predefined Methods: Provides useful methods like name() , ordinal() , and values() .
Declaring an Enum
enum Day {
MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY, SUND
AY
}
Enums 1
}
}
Output:
Enum Features
1. Iterating Over Enum Constants
You can use the values() method to loop through all enum constants.
enum Color {
RED, GREEN, BLUE
}
Output:
RED
GREEN
BLUE
Enums 2
enum Season {
SPRING, SUMMER, FALL, WINTER
}
enum Planet {
MERCURY(3.30e23, 2.44e6),
EARTH(5.97e24, 6.37e6),
JUPITER(1.90e27, 6.99e7);
Enums 3
public class Main {
public static void main(String[] args) {
for (Planet p : Planet.values()) {
System.out.printf("%s: Surface Gravity = %.2f m/s^2%n",
p, p.surfaceGravity());
}
}
}
Output:
Important Questions
Enums 4
2. Can enums extend classes or implement interfaces?
Enums can implement interfaces, which allows them to inherit behavior from
the interface.
interface Printable {
void print();
}
@Override
public void print() {
System.out.println(this + " level");
}
}
Yes, you can define an enum inside a class, either as a static or non-static
member.
Enums 5
Direction dir = Direction.NORTH;
System.out.println("Direction: " + dir); // Output: Direction: NORTH
}
}
Yes, enums can have constructors, but they are private or package-private by
default. They are used to initialize fields in the enum constants.
enum Color {
RED("Stop"), GREEN("Go"), YELLOW("Caution");
Color(String meaning) {
this.meaning = meaning;
}
Yes, an enum can have abstract methods. Each constant must then provide an
implementation for the method.
Enums 6
enum Operation {
ADD {
@Override
public int apply(int a, int b) {
return a + b;
}
},
SUBTRACT {
@Override
public int apply(int a, int b) {
return a - b;
}
};
Yes, an enum can have a main() method like any other class.
enum Greeting {
HELLO, HI, HEY;
Enums 7
}
}
Enum constants are unique. If you try to define two constants with the same
name, the compiler will throw an error.
Enums are implemented as a special type of class. Each enum constant is a static
and final instance of the enum. The constants are initialized when the enum class
is loaded.
Enums 8
Packages
In Java, packages are a way to organize and group related classes and interfaces.
They act like folders on your computer to keep your code neat and manageable.
Packages also help avoid name conflicts between classes.
2. Avoid Name Conflicts: Different packages can have classes with the same
name.
3. Access Control: Define which classes can be accessed outside the package.
Types of Packages
The folder structure for Java packages should match the package name. Each
part of the package name corresponds to a folder. Let's break it down with an
example.
ProjectFolder
├── Main.java
Packages 1
└── mypackage
└── Calculator.java
Packages 2
2. Compile the Calculator class:
javac mypackage/Calculator.java
javac Main.java
java Main
Packages 3
Real life Examples
Object:
myRemote (an instance of TVRemote ) with brand = "Sony" , color = "Black" , and
batteryLevel = 100 .
Explanation:
The TVRemote class defines what a remote is (its properties and behaviors).
The myRemote object is a specific remote with its own values for the properties.
2. Encapsulation
Class: TVRemote
Explanation:
To check the battery level, you must use the public method checkBatteryLevel() .
3. Polymorphism
Method Overloading:
Method Overriding:
Explanation:
Overriding: The SmartTVRemote class provides a specific way to turn on the TV,
different from the general TVRemote class.
4. Inheritance
Superclass: TVRemote
Explanation:
The SmartTVRemote class inherits the properties and behaviors of the TVRemote
Explanation:
The Remote class defines a common structure for all remotes but leaves the
implementation of controlDevice() to its subclasses.
6. Interfaces
Interface: PowerControl
Explanation:
Object:
myPen(an instance of Pen ) with brand = "Parker" , color = "Blue" , inkLevel = 80 , tipSize
Explanation:
The Pen class is like a blueprint that defines the common characteristics and
behaviors of all pens.
The myPen object is a specific pen with its own values for these properties.
Explanation:
The checkInkLevel() method allows controlled access to check the ink level.
Explanation:
method.
Explanation:
Explanation:
Explanation:
The Writable interface ensures that any erasable pen must provide methods for
write() and erase() .
Class: A Car is a blueprint that defines common properties like brand , model ,
color , and behaviors like start() , stop() , and accelerate() .
Object: A specific car, like a red Tesla Model 3, is an instance of the Car
class.
In Real Life: The Car class is like a blueprint in a factory, while a specific car you
own is an object of that class.
In Real Life: Encapsulation ensures that sensitive data (balance) is only modified
through defined methods and is not directly accessible.
In Real Life: A coffee machine provides the same function ( makeCoffee() ), but with
different arguments (parameters).
However, the actual payment process differs based on whether the user pays
with a credit card, net banking, UPI etc.
In Real Life:
At runtime, Java determines which method to call based on the actual object
type.
In Real Life: A Car "is-a" Vehicle, meaning it inherits all vehicle behaviors but can
also add new ones.
Explanation: