Java Threads Introduction 🎯

beginner
5 min

Java Threads Introduction 🎯

Welcome to the Java Threads Introduction lesson! In this tutorial, we'll dive into the world of multi-threading in Java, a powerful feature that allows your programs to perform multiple tasks simultaneously. Let's get started! 🚀

What are Threads? 📝

Threads are independent paths of execution within a program. They allow the execution of multiple tasks within a single Java application. When you run a program, by default it has one thread called the main thread.

Quick Quiz
Question 1 of 1

How many threads does a Java program have when it starts?

Creating Threads in Java 💡

Java provides two methods for creating threads:

  1. Extending the Thread class
  2. Implementing the Runnable interface

We'll focus on creating threads by extending the Thread class for simplicity.

Creating a Thread Class 📝

First, create a new class that extends Thread. In the class, override the run() method, where you'll write the code for the thread to execute.

java
public class MyThread extends Thread { public void run() { // Your code here } }

Starting a Thread 💡

To start a thread, create an instance of your thread class and call the start() method.

java
MyThread thread = new MyThread(); thread.start();

Synchronization in Threads 📝

When multiple threads access shared data, synchronization becomes crucial to prevent data inconsistencies. Java provides synchronized blocks and methods for this purpose.

java
public class MySyncThread extends Thread { int count = 0; public synchronized void increment() { count++; } public void run() { for(int i = 0; i < 1000; i++) { increment(); } } }

In this example, the increment() method is synchronized, ensuring that only one thread can access the count variable at a time.

Example: Producer-Consumer Problem 🎯

Let's solve a classic problem using Java threads: the producer-consumer problem. The goal is to have two threads, one producing data (producer) and one consuming data (consumer), while ensuring that the buffer never exceeds a certain size.

java
class Buffer { private int maxSize; private int buffer[]; private int producer = 0; private int consumer = 0; private boolean isFull = false; private boolean isEmpty = true; public Buffer(int size) { maxSize = size; buffer = new int[maxSize]; } public synchronized void put(int value) throws InterruptedException { while (isFull) { wait(); } buffer[producer] = value; producer = (producer + 1) % maxSize; isFull = (producer == consumer); if (!isEmpty) { notify(); } } public synchronized int take() throws InterruptedException { while (isEmpty) { wait(); } int value = buffer[consumer]; consumer = (consumer + 1) % maxSize; isEmpty = (consumer == producer); if (!isFull) { notify(); } return value; } } class Producer extends Thread { Buffer buffer; public Producer(Buffer buffer) { this.buffer = buffer; } public void run() { for(int i = 0; i < 10; i++) { try { buffer.put(i); sleep(100); } catch (InterruptedException e) { e.printStackTrace(); } } } } class Consumer extends Thread { Buffer buffer; public Consumer(Buffer buffer) { this.buffer = buffer; } public void run() { for(int i = 0; i < 10; i++) { try { buffer.take(); sleep(150); } catch (InterruptedException e) { e.printStackTrace(); } } } }

In this example, we've created a Buffer class to manage the shared data and synchronized methods for putting and taking items. The Producer and Consumer classes represent the threads that produce and consume data, respectively.

Conclusion 🎯

In this tutorial, we've learned the basics of creating and managing threads in Java. Multi-threading is a powerful tool that allows your programs to perform multiple tasks simultaneously, making them more responsive and efficient.

Don't forget to practice and experiment with the producer-consumer example to get a better understanding of synchronization in threads. Happy coding! 🎉

Keep learning and exploring Java's vast features at CodeYourCraft! 🌟