Topic 71 of 119 6. Object-Oriented Programming in Java Interactive Tutorial

The instanceof Operator: Type Checking and Pattern Matching

9 mins read Last updated: 22 Aug 2026 27,283 views

Direct Answer & Core Concept

When working with Java inheritance, interfaces, and objects, you may sometimes need to know what type of object you are actually dealing with.

For example, a variable may have a parent class type, but the object stored inside it could belong to a child class.

This is where the instanceof operator in Java becomes useful.

The instanceof operator allows you to check whether an object belongs to a particular class, subclass, or interface type.

Modern Java also provides pattern matching with instanceof, which makes type checking and casting shorter and easier to read.

In this tutorial, you will learn:

  • What instanceof means in Java

  • How the instanceof operator works

  • Java instanceof syntax

  • Checking objects with instanceof

  • instanceof with inheritance

  • instanceof with interfaces

  • instanceof with null

  • Using instanceof before type casting

  • Pattern matching with instanceof

  • Pattern variable scope

  • Negating an instanceof pattern

  • Common mistakes

  • instanceof vs type casting

  • Practical examples

  • Frequently asked questions

Detailed Explanation & Mechanics

What Is the instanceof Operator in Java?

The instanceof operator in Java is used to check whether an object is an instance of a particular type.

It returns a boolean value:

or

The basic syntax is:

For example:

Main.java
Run Online
String name = "Java";
System.out.println(name instanceof String);

Output:

The object stored in name is a String, so the expression returns true.


Simple Example of instanceof

Let's start with a very simple example.

Main.java
Run Online
public class Main {
    public static void main(String[] args) {
        String language = "Java";
        if (language instanceof String) {
            System.out.println("The object is a String");
        }
    }
}

Output:

Here:

Main.java
Run Online
language instanceof String

asks Java:

"Is the object referred to by language a String?"

The answer is true.

Tutorial illustration


instanceof Syntax in Java

The traditional syntax is:

Main.java
Run Online
object instanceof ClassName

Example:

Main.java
Run Online
Object value = "Hello";
if (value instanceof String) {
    System.out.println("value is a String");
}

You can also store the result in a boolean variable:

Main.java
Run Online
Object value = "Hello";
boolean result = value instanceof String;
System.out.println(result);

Output:

So instanceof produces a boolean result.


Why Do We Need instanceof?

Java supports inheritance and polymorphism.

Suppose we have:

Main.java
Run Online
class Animal {
}class Dog extends Animal {
}class Cat extends Animal {
}

Now we can create:

Main.java
Run Online
Animal animal = new Dog();

The variable type is Animal, but the actual object is a Dog.

If you need to determine the object's runtime type, instanceof can help.

Main.java
Run Online
if (animal instanceof Dog) {
    System.out.println("This is a Dog");
}

Output:

This is one of the most common situations where beginners encounter the instanceof operator.


instanceof with Inheritance

Let's look at inheritance more closely.

Main.java
Run Online
class Animal {
    void eat() {
        System.out.println("Animal is eating");
    }
}class Dog extends Animal {
    void bark() {
        System.out.println("Dog is barking");
    }
}

Now:

Main.java
Run Online
Animal animal = new Dog();

Although the reference type is Animal, the actual object is Dog.

We can check it:

Main.java
Run Online
if (animal instanceof Dog) {
    System.out.println("animal refers to a Dog");
}

Output:

This happens because a Dog object is also an Animal.


instanceof with Parent and Child Classes

Consider:

Main.java
Run Online
class Animal {
}class Dog extends Animal {
}

Now:

Main.java
Run Online
Dog dog = new Dog();
System.out.println(dog instanceof Dog);
System.out.println(dog instanceof Animal);

Output:

Why is the second result also true?

Because Dog inherits from Animal.

So a Dog object is also considered an Animal.

Think of the relationship like this:

Therefore:

Main.java
Run Online
Dog object | +-- is a Dog → true | +-- is an Animal → true

instanceof with Multiple Types

You can use multiple instanceof checks when different types need different behavior.

Example:

Main.java
Run Online
class Animal {
}class Dog extends Animal {
}class Cat extends Animal {
}

Then:

Main.java
Run Online
Animal animal = new Cat();
if (animal instanceof Dog) {
    System.out.println("Dog");
} else if (animal instanceof Cat) {
    System.out.println("Cat");
} else {
    System.out.println("Unknown animal");
}

Output:

This can be useful when processing objects from a common parent type.


instanceof with Interfaces

The instanceof operator is not limited to classes.

It can also check whether an object implements an interface.

Example:

Main.java
Run Online
interface Printable {
    void print();
}class Report implements Printable {
    public void print() {
        System.out.println("Printing report");
    }
}

Now:

Main.java
Run Online
Report report = new Report();
if (report instanceof Printable) {
    System.out.println("Report implements Printable");
}

Output:

Main.java
Run Online
Report implements Printable

This is useful when working with interface-based designs.


instanceof and null

One important rule is:

null instanceof AnyType always returns false.

Example:

Main.java
Run Online
String value = null;
System.out.println(value instanceof String);

Output:

Java does not throw a NullPointerException for this check.

For example:

Main.java
Run Online
Object value = null;
if (value instanceof String) {
    System.out.println("String");
} else {
    System.out.println("Not a String");
}

Output:

This is a useful property of instanceof.


instanceof Before Type Casting

Before modern pattern matching, instanceof was often used together with explicit casting.

For example:

Main.java
Run Online
Object value = "Hello Java";
if (value instanceof String) {
    String text =(String) value;
    System.out.println(text.length());
}

There are two steps:

Step 1: Check the type

Step 2: Cast the object

Main.java
Run Online
String text =(String) value;

This approach is still valid Java.

However, modern Java provides a shorter approach using pattern matching.


What Is Pattern Matching with instanceof?

Pattern matching for instanceof allows Java to combine:

  1. Type checking

  2. Type casting

  3. Variable declaration

into one expression.

Instead of writing:

Main.java
Run Online
if (value instanceof String) {
    String text =(String) value;
    System.out.println(text.length());
}

you can write:

Main.java
Run Online
if (value instanceof String text) {
    System.out.println(text.length());
}

This is called pattern matching for instanceof.

The variable text is automatically created after Java confirms that value is a String.


Simple instanceof Pattern Matching Example

Main.java
Run Online
public class Main {
    public static void main(String[] args) {
        Object value = "Hello Java";
        if (value instanceof String text) {
            System.out.println("Length: " + text.length());
        }
    }
}

Output:

The important part is:

Main.java
Run Online
value instanceof String text

Here:

  • value is the object being checked.

  • String is the type.

  • text is the pattern variable.

If the check succeeds, text can be used as a String.


Traditional instanceof vs Pattern Matching

Here is the difference.

Traditional approach

Main.java
Run Online
Object value = "Java";
if (value instanceof String) {
    String text =(String) value;
    System.out.println(text.toUpperCase());
}

Pattern matching approach

Main.java
Run Online
Object value = "Java";
if (value instanceof String text) {
    System.out.println(text.toUpperCase());
}

The second version avoids repeating the type and explicit cast.

It is generally easier to read.


Pattern Variable in instanceof

The variable created by pattern matching is called a pattern variable.

Example:

Main.java
Run Online
Object value = "Java";
if (value instanceof String text) {
    System.out.println(text);
}

Here:

is the pattern variable.

Inside the successful branch, Java knows that text is a String.

Therefore, you can call String methods:

Main.java
Run Online
if (value instanceof String text) {
    System.out.println(text.length());
    System.out.println(text.toUpperCase());
}

Scope of an instanceof Pattern Variable

One important concept is the scope of a pattern variable.

Consider:

Main.java
Run Online
Object value = "Java";
if (value instanceof String text) {
    System.out.println(text.length());
}

The variable text is available inside the part of the program where Java knows that the condition is true.

You cannot normally use it outside that valid scope:

Main.java
Run Online
Object value = "Java";
if (value instanceof String text) {
    System.out.println(text.length());
}// text is not available here

This prevents Java from using a variable when its type has not been safely established.


instanceof with Logical AND

Pattern matching becomes especially useful with &&.

Example:

Main.java
Run Online
Object value = "Java";
if (value instanceof String text && text.length() > 3) {
    System.out.println("Long string: " + text);
}

Here Java first checks:

Main.java
Run Online
value instanceof String text

If that succeeds, Java can safely evaluate:

This lets you perform the type check and additional condition together.


instanceof with Logical OR

Be careful when using pattern variables with ||.

For example:

Main.java
Run Online
if (value instanceof String text || text.length() > 3) {
}

This is not valid in the same way because the second condition could be evaluated when the first condition is false. In that situation, Java cannot guarantee that text exists.

A useful rule is:

A pattern variable must be definitely matched before you use it.

For beginners, && is often easier to understand because the second condition is evaluated only after the first condition succeeds.


Negating instanceof

You can also use ! with instanceof.

Example:

Main.java
Run Online
Object value = 100;
if (!(value instanceof String)) {
    System.out.println("The value is not a String");
}

Output:

Main.java
Run Online
The value is not a String

This is useful when you want to handle the "not this type" case first.


Pattern Matching with Negation

Modern Java can also use a pattern variable with a negated condition.

For example:

Main.java
Run Online
Object value = "Java";
if (!(value instanceof String text)) {
    return;
}System.out.println(text.length());

After the early exit, Java knows that the remaining code can safely use text as a String.

This style can make longer methods easier to read because the invalid case is handled early.


instanceof with Numbers

You can use instanceof with wrapper classes such as Integer, Double, and Long.

Example:

Main.java
Run Online
Object value = 100;
if (value instanceof Integer number) {
    System.out.println("Number: " + number);
}

Output:

Remember that Java's primitive types such as int are not objects.

This is why you normally check an object containing an Integer, not an int itself.


instanceof with String

Strings are one of the easiest examples.

Main.java
Run Online
Object value = "Hello";
if (value instanceof String text) {
    System.out.println("String value: " + text);
}

Output:

You can then use any appropriate String methods:

Main.java
Run Online
if (value instanceof String text) {
    System.out.println(text.length());
    System.out.println(text.toLowerCase());
}

instanceof with Collections

You can also check whether an object implements a collection interface.

For example:

Main.java
Run Online
Object value = new ArrayList<String>();
if (value instanceof List<?>) {
    System.out.println("This object is a List");
}

Notice the use of:

rather than:

Java generally cannot use instanceof to test a parameterized generic type such as List<String> directly because generic type arguments are erased at runtime.

This is an important concept related to type erasure.


Why Can't We Use instanceof List<String>?

This is not valid:

Main.java
Run Online
if (value instanceof List<String>) {
}

Java does not retain the generic type argument String at runtime in a way that allows this direct check.

Instead, use:

Main.java
Run Online
if (value instanceof List<?>) {
}

This checks whether the object is a List without claiming a particular element type.


instanceof and Type Casting Are Different

It is important not to confuse instanceof with casting.

instanceof

Checks whether an object belongs to a type.

The result is:

or:

Type casting

Converts the reference to another compatible reference type.

Main.java
Run Online
String text =(String) value;

Casting does not simply return true or false.

If the runtime object is not compatible with the target reference type, an inappropriate cast can throw ClassCastException.

That's one reason type checking with instanceof can be useful before an explicit cast.


Complete Example: instanceof with Inheritance

Let's put the concepts together.

Main.java
Run Online
class Animal {
    void eat() {
        System.out.println("Animal is eating");
    }
}class Dog extends Animal {
    void bark() {
        System.out.println("Dog is barking");
    }
}class Cat extends Animal {
    void meow() {
        System.out.println("Cat is meowing");
    }
}public class Main {
    public static void main(String[] args) {
        Animal animal = new Dog();
        if (animal instanceof Dog dog) {
            dog.bark();
        } else if (animal instanceof Cat cat) {
            cat.meow();
        }
    }
}

Output:

Here, the variable animal has the type Animal, but the actual object is a Dog.

Pattern matching lets us safely access the Dog-specific method.


A Real-World Example

Imagine an application that processes different types of payments.

Main.java
Run Online
class Payment {
}class CreditCardPayment extends Payment {
    void processCard() {
        System.out.println("Processing credit card");
    }
}class UpiPayment extends Payment {
    void processUpi() {
        System.out.println("Processing UPI");
    }
}

Now a method can receive the common parent type:

Main.java
Run Online
static void processPayment(Payment payment) {
    if (payment instanceof CreditCardPayment card) {
        card.processCard();
    } else if (payment instanceof UpiPayment upi) {
        upi.processUpi();
    }
}

The method can accept a Payment, then determine the specific object type when needed.

This is a practical example of type checking using instanceof.


instanceof with final Classes

If a class is final, Java knows that no class can extend it.

For example:

You can still use:

Main.java
Run Online
Object value = new Dog();
if (value instanceof Dog dog) {
    System.out.println("Dog object");
}

The check works normally.

The important difference is that no subclass of Dog can exist because Dog is final.


instanceof and Interfaces in Real Programs

Suppose an application has a common interface:

Main.java
Run Online
interface Printable {
    void print();
}

Several classes can implement it:

Main.java
Run Online
class Invoice implements Printable {
    public void print() {
        System.out.println("Printing invoice");
    }
}class Report implements Printable {
    public void print() {
        System.out.println("Printing report");
    }
}

You can check the object type:

Main.java
Run Online
Object document = new Invoice();
if (document instanceof Printable printable) {
    printable.print();
}

Output:

This demonstrates how instanceof can work with interfaces as well as classes.


instanceof and Polymorphism

instanceof is often encountered when learning polymorphism.

Consider:

Main.java
Run Online
Animal animal = new Dog();

This is polymorphism because an Animal reference points to a Dog object.

You can check the actual object type:

Main.java
Run Online
if (animal instanceof Dog dog) {
    dog.bark();
}

However, don't use instanceof everywhere simply because it is available.

Good object-oriented design often relies on polymorphism itself.

For example, if every Animal has a makeSound() method, it may be cleaner to call:

rather than repeatedly checking whether the object is a Dog, Cat, or another subclass.

instanceof is most useful when the specific type genuinely matters.


Common Mistakes with instanceof

Mistake 1: Checking a primitive

You cannot use instanceof directly with primitive values.

For example:

You cannot treat number itself as an object for an instanceof test.

Instead, an object such as Integer can be checked:

Main.java
Run Online
Object number = 10;
if (number instanceof Integer) {
    System.out.println("Integer");
}

Mistake 2: Confusing instanceof with casting

This:

checks the type.

This:

performs a cast.

They have different purposes.


Mistake 3: Assuming instanceof changes the object

It does not.

only checks the object's type.

It does not convert the object into a String.


Mistake 4: Forgetting about null

Remember:

is:


Mistake 5: Using generic type arguments directly

This is not valid:

Main.java
Run Online
value instanceof List<String>

Use:

when appropriate.


instanceof vs getClass()

Beginners sometimes ask why they should use instanceof instead of getClass().

They are not exactly the same.

Consider:

Main.java
Run Online
class Animal {
}class Dog extends Animal {
}

Then:

Main.java
Run Online
Dog dog = new Dog();
System.out.println(dog instanceof Animal);

This returns:

because a Dog is an Animal.

But:

Main.java
Run Online
System.out.println(dog.getClass() == Animal.class);

returns:

because the actual class is Dog, not Animal.

So:

instanceof

Checks whether the object is compatible with a type, including applicable superclass/interface relationships.

getClass()

Gives the object's actual runtime class.


instanceof vs Type Casting

FeatureinstanceofType casting
Main purposeCheck object typeTreat reference as another compatible type
Returns boolean?YesNo
Can prevent unsafe cast?Yes, when used appropriatelyNo
Exampleobj instanceof String(String) obj
Pattern matching available?YesNo

A common older pattern is:

Main.java
Run Online
if (obj instanceof String) {
    String text =(String) obj;
}

Modern Java can simplify this to:

Main.java
Run Online
if (obj instanceof String text) {
    System.out.println(text);
}

Benefits of Pattern Matching with instanceof

Pattern matching makes type-checking code shorter and clearer.

Less code

Instead of:

Main.java
Run Online
if (obj instanceof String) {
    String text =(String) obj;
}

you can write:

Main.java
Run Online
if (obj instanceof String text) {
}

No repeated cast

The type conversion is handled as part of the pattern.

Better readability

The condition tells you both what is being checked and what variable becomes available.

Safer code

The pattern variable is only available where Java knows the type check has succeeded.


Quick Visual Guide to instanceof

Main.java
Run Online
instanceof | Checks object type | +-----------+-----------+ | | | Class Subclass Interface | | | String Dog Printable | | | +-----------+-----------+ | true / false

With pattern matching:

Architecture Diagram
Object
  |
  | instanceof String text
  |
  +------ false ------> Pattern not matched
  |
  +------ true -------> text is available as String

Frequently Asked Questions

What does instanceof mean in Java?

instanceof is an operator that checks whether an object is an instance of a specified class, subclass relationship, or interface type.

What does instanceof return?

It returns a boolean value: true or false.

Can instanceof check interfaces?

Yes. You can use instanceof to check whether an object implements an interface.

What happens when instanceof is used with null?

The result is always false.

returns:

Can instanceof be used with primitive types?

No. instanceof works with reference types and objects, not primitive values such as int, double, or boolean.

What is pattern matching for instanceof?

Pattern matching combines type checking with the declaration of a variable.

Instead of:

Main.java
Run Online
if (obj instanceof String) {
    String text =(String) obj;
}

you can use:

Main.java
Run Online
if (obj instanceof String text) {
}

Is pattern matching the same as casting?

No. Pattern matching performs a type test and makes a correctly typed pattern variable available when the test succeeds. It avoids the need for a separate explicit cast in that common situation.

Can I use instanceof with generics?

You cannot directly test a parameterized type such as:

because of type erasure.

You can check:

instead.

What is the difference between instanceof and getClass()?

instanceof checks whether an object is compatible with a type. getClass() gives the object's actual runtime class.

Should I use instanceof everywhere?

No. It is useful when the specific runtime type matters, but many object-oriented designs are cleaner when they rely on polymorphism instead of repeatedly checking subclasses.


Practice Questions

Try these examples yourself.

Question 1

What will this print?

Main.java
Run Online
Object value = "Java";
System.out.println(value instanceof String);

Answer:


Question 2

What will this print?

Main.java
Run Online
Object value = null;
System.out.println(value instanceof String);

Answer:


Question 3

What does this code do?

Main.java
Run Online
Object value = "Hello";
if (value instanceof String text) {
    System.out.println(text.length());
}

Answer:

It checks whether value is a String. If it is, text becomes available as a String inside the valid pattern scope.


Question 4

Is this valid?

Main.java
Run Online
Object value = new ArrayList<String>();
if (value instanceof List<String>) {
}

Answer:

No. A parameterized generic type such as List<String> cannot normally be used directly in an instanceof check because of type erasure.


Question 5

What is the difference between these?

and:

Answer:

The first checks the type and returns a boolean. The second explicitly casts the reference to String.


Final Summary

The instanceof operator in Java is mainly used when you need to determine whether an object is compatible with a particular type.

The basic form is:

It returns either true or false.

With inheritance:

Main.java
Run Online
Animal animal = new Dog();
if (animal instanceof Dog) {
    System.out.println("Dog");
}

Java also provides pattern matching:

Main.java
Run Online
if (animal instanceof Dog dog) {
    dog.bark();
}

This combines the type check with a usable pattern variable.

Remember these four ideas:

Main.java
Run Online
instanceof↓Checks an object's type

true / false
↓
Result of the check

instanceof Type variable
↓
Pattern matching

null instanceof Type
↓
Always false

Once you understand instanceof, you will have an easier time working with inheritance, polymorphism, interfaces, type casting, and modern Java pattern matching.

Runnable Code Example: The instanceof Operator

Java 17+
Main.java
Run Online
public class InstanceofDemo {
    public static void processObject(Object obj) {
        // Modern Pattern Matching for instanceof (Java 16+)
        if (obj instanceof String s && s.length() > 0) {
            System.out.println("String uppercase: " + s.toUpperCase());
        } else if (obj instanceof Integer i) {
            System.out.println("Integer squared: " +(i * i));
        } else {
            System.out.println("Unknown or null object: " + obj);
        }
    } public static void main(String[] args) {
        processObject("Java 21");
        processObject(5);
        processObject(null);
    }
}

Common Java Technical Interview Questions & Answers

Interview Prep
Q1

What does null instanceof AnyClass evaluate to in Java?

It evaluates to false.
Q2

How does Pattern Matching for instanceof improve code readability?

It combines the type check and explicit casting step into a single clean declaration with scoped pattern variables.

Key Takeaways, Best Practices & Clean Code Rules

Java Best Practice & Production Rules

Use modern pattern matching for instanceof (Java 16+) to eliminate ugly explicit class casts throughout your business logic.