Extends Thread or implements Runnable: How to Ace Your Interview

Online Python Trainer for Beginners

Learn Python easily without overwhelming theory. Solve practical tasks with automatic checking, get hints in Russian, and write code directly in your browser — no installation required.

Start Course

implements Runnable vs extends Thread: Why 90% of Java Developers Get It Wrong?

\n\n

Imagine you're at an interview for a major IT company. The HR manager smiles and asks a "simple" question: "What is the difference between implements Runnable and extends Thread in Java?". It seems simple, right? But according to Stack Overflow, even experienced developers stumble here. Thousands of views, hundreds of comments — the topic "Java Runnable vs Thread" remains one of the hottest.

\n\n

In this article, we won't just list the differences. We'll break down the top 5 real-world mistakes programmers make and show you how to write clean, scalable multithreaded code. If you write in Java and use Thread directly — read carefully. You might be creating problems for yourself without even realizing it.

\n\n

Quick Primer: What are Thread and Runnable?

\n\n

Before diving into the details, let's refresh the basics. Java Thread is a class representing an execution thread. It can run code in parallel. Runnable is a functional interface with a single method run(). It describes a task to be executed but doesn't know how to launch it.

\n\n

Here's a classic example with extends Thread:

\n\n
public class MyThread extends Thread {\n    @Override\n    public void run() {\n        System.out.println("Thread is running: " + Thread.currentThread().getName());\n    }\n\n    public static void main(String[] args) {\n        MyThread t = new MyThread();\n        t.start(); // Starting a new thread\n    }\n}
\n\n

And here's the same functionality using implements Runnable:

\n\n
public class MyTask implements Runnable {\n    @Override\n    public void run() {\n        System.out.println("Task is executing: " + Thread.currentThread().getName());\n    }\n\n    public static void main(String[] args) {\n        Thread t = new Thread(new MyTask());\n        t.start();\n    }\n}
\n\n

At first glance, the difference is minimal. But the devil, as always, is in the details.

\n\n

Top 5 Mistakes When Working with Thread and Runnable

\n\n

Mistake #1: Extending Thread When You Should Use Runnable

\n\n

The most common problem is tight coupling with the Thread class. When you write extends Thread, your class becomes a thread. You lose the ability to inherit from another class. Java is a single-inheritance language, and this is a serious limitation.

\n\n

Example of bad code:

\n\n
public class DataProcessor extends Thread {\n    // Can no longer extend JFrame, ArrayList, or any other useful class\n    @Override\n    public void run() {\n        // data processing\n    }\n}
\n\n

How it should be done: Use implements Runnable. It's an interface — you can implement it in any class that already extends something else.

\n\n
public class DataProcessor extends BaseService implements Runnable {\n    @Override\n    public void run() {\n        // data processing\n    }\n}
\n\n

Mistake #2: Confusing run() and start()

\n\n

A classic. Beginners (and not only) often call run() instead of start(). The difference is critical: start() creates a new thread and calls run() inside it. run(), on the other hand, executes in the current thread like a regular method.

\n\n

Example of the mistake:

\n\n
Thread t = new Thread(new MyTask());\nt.run(); // It works, but in the same thread! No multithreading.
\n\n

The console output will be in the main main thread, not a new one. This error is hard to catch because the code doesn't crash — it just doesn't do what you expect.

\n\n

How to avoid it: Always use start() to launch a new thread. If you're unsure

Blogs

Book Recommendations