Language
日本語
English

Caution

JavaScript is disabled in your browser.
This site uses JavaScript for features such as search.
For the best experience, please enable JavaScript before browsing this site.

Java Dictionary

  1. Home
  2. Java Dictionary
  3. Beginners Guide: Overview, Features, and Learning Path

Beginners Guide: Overview, Features, and Learning Path

A guide to understanding the big picture of Java — what it is, its key features, how code executes, and a recommended learning path through this dictionary.

What Is Java

Java is a programming language released in 1995 by Sun Microsystems (now Oracle). In short, it is a language designed so that code written once can run on any operating system.

This idea is captured in the slogan "Write Once, Run Anywhere." A program compiled on Windows can run on Linux or macOS without modification. The JVM (Java Virtual Machine), described below, is what makes this possible.

Where Java Is Used

Java is widely used in the following areas today.

  • Web application backends (Spring Boot and similar frameworks)
  • Android app development (an official language for Android alongside Kotlin)
  • Large-scale enterprise and financial systems
  • Microservices and cloud-native systems

Java became the dominant language for enterprise systems from the late 1990s through the 2000s, and that software continues to run in organizations around the world today.

Java's Characteristics — Strengths and Tradeoffs

Java has distinct characteristics compared to other languages, each of which can be a strength or a tradeoff depending on the situation. This is not a question of which is better — the fit depends on project scale, goals, and team structure.

Statically Typed Language

Java requires types to be declared explicitly for variables, method parameters, and return values. Type mismatches are detected at compile time (before execution).

// Declare variables with explicit types
String name = "Gojo Satoru";
int power = 9999;

// Assigning the wrong type causes a compile error
// name = 100; // Error: incompatible types

Explicit types mean more code to write, but IDE (Integrated Development Environment — a tool combining code editing, execution, and debugging) autocompletion becomes more powerful and type mismatch bugs can be caught before the program runs — especially valuable in large codebases.

Garbage Collection

In C and C++, the programmer must manually allocate and free memory. In Java, the garbage collector (GC) automatically reclaims memory that is no longer in use.

This removes the burden of manual memory management, but the GC may cause brief pauses when it runs (known as "GC pauses"). In systems where real-time responsiveness is critical, these pauses can be a concern.

Object-Oriented Language

Java is designed around classes and objects. All logic is written inside classes, grouping data and behavior together.

// Class definition
class Fighter {
    String name;
    int power;

    void attack() {
        System.out.println(name + " attacks!");
    }
}

// Create an instance
Fighter gojo = new Fighter();
gojo.name = "Gojo Satoru";
gojo.power = 9999;
gojo.attack(); // Gojo Satoru attacks!

Cross-Platform

Compiling Java code does not produce machine code for a specific OS or CPU (Central Processing Unit — the processor that executes computations). Instead, it produces bytecode (.class files). Bytecode runs on the JVM, so the same program can run on any OS where a JVM is available.

Strengths and Tradeoffs (Neutral Comparison)

AspectNotes
Type safetyStatic typing catches bugs before execution. More code to write for type declarations.
Memory managementGC handles it automatically. GC pauses can be an issue in latency-sensitive systems.
PerformanceJIT compilation makes execution fast. JVM startup overhead exists.
EcosystemLarge selection of libraries and frameworks. Dependencies can grow large.
VerbosityType declarations and class definitions add boilerplate. IDE completion helps.
PortabilityRuns anywhere a JVM is available. JVM setup is required.
Learning curveRequires understanding OOP and the type system. Abundant learning resources available.

How Execution Works — .java → javac → .class → JVM

Running Java code involves two stages.

Source Code (.java file) javac (compile) Bytecode (.class file) JVM (run) Program Runs (any OS) JVM (Java Virtual Machine) Translates bytecode to native machine code at runtime. Windows / Linux / macOS — runs wherever a JVM exists.

Seeing It in Action

Create a file called Hello.java.

Hello.java
public class Hello {
    public static void main(String[] args) {
        System.out.println("Hello, Gojo Satoru!");
    }
}

Compile and run.

javac Hello.java
java Hello
Hello, Gojo Satoru!

The javac command compiles the source into Hello.class (bytecode). The java command runs that bytecode on the JVM.

JIT (Just-In-Time) Compilation

The JVM interprets bytecode line by line, but frequently executed code paths are compiled into native machine code and cached at runtime. This is called JIT compilation. Programs tend to run slowly right after startup and speed up as the JIT warms up.

Variables and Types

Java is a statically typed language, so the type of each variable must be declared explicitly.

// Primitive types
int power = 9999;              // integer (-2^31 to 2^31-1)
long bigNumber = 10000000000L; // large integer (L suffix required)
double height = 175.5;         // floating-point (double precision)
float ratio = 0.8f;            // floating-point (single precision, f suffix required)
boolean isSorcerer = true;     // boolean
char initial = 'G';            // single character (single quotes)

// Reference type
String name = "Gojo Satoru";  // text string (double quotes)

Note that String starts with a capital letter. Types like int and boolean are primitive types (they store the value directly), while String is a reference type (it stores a reference to an object).

var (Java 10 and Later)

From Java 10 onward, var enables type inference. The compiler infers the type from the right-hand side of the assignment.

// Using var (type inference)
var name = "Itadori Yuji";  // inferred as String
var power = 9999;           // inferred as int

// Equivalent to explicit declarations
String name2 = "Itadori Yuji";
int power2 = 9999;

var can only be used for local variables. It cannot be used for fields or method parameters.

For more on variables and types, see Creating and Running .java Files.

Classes and Objects

Java is an object-oriented language. Data (fields) and behavior (methods) are grouped into classes. An instance (object) is created from a class and used at runtime.

class Sorcerer {
    // Fields (data)
    String name;
    int cursedEnergy;

    // Constructor (called when an instance is created)
    Sorcerer(String name, int cursedEnergy) {
        this.name = name;
        this.cursedEnergy = cursedEnergy;
    }

    // Method (behavior)
    void introduce() {
        System.out.println("Sorcerer: " + name + " (Cursed Energy: " + cursedEnergy + ")");
    }
}

// Create instances
Sorcerer gojo = new Sorcerer("Gojo Satoru", 9999);
Sorcerer itadori = new Sorcerer("Itadori Yuji", 500);

gojo.introduce();    // Sorcerer: Gojo Satoru (Cursed Energy: 9999)
itadori.introduce(); // Sorcerer: Itadori Yuji (Cursed Energy: 500)

Inheritance (extends)

A new class can inherit the fields and methods of an existing class.

// Parent class
class Sorcerer {
    String name;

    void curse() {
        System.out.println(name + " used a cursed technique!");
    }
}

// Child class (inherits from Sorcerer)
class SpecialGrade extends Sorcerer {
    // Override the parent's method
    @Override
    void curse() {
        System.out.println(name + " used Limitless!");
    }
}

SpecialGrade gojo = new SpecialGrade();
gojo.name = "Gojo Satoru";
gojo.curse(); // Gojo Satoru used Limitless!

For more on classes, see new / Class Definition / Constructor. For inheritance, see extends / Override.

Collections — ArrayList / HashMap

Arrays have a fixed length. ArrayList allows elements to be added and removed dynamically.

ArrayList

import java.util.ArrayList;

ArrayList<String> members = new ArrayList<>();
members.add("Gojo Satoru");
members.add("Itadori Yuji");
members.add("Fushiguro Megumi");

System.out.println(members.get(0));  // Gojo Satoru
System.out.println(members.size());  // 3

members.remove("Gojo Satoru");
System.out.println(members.size());  // 2

HashMap

HashMap stores data as key-value pairs.

import java.util.HashMap;

HashMap<String, Integer> cursedEnergy = new HashMap<>();
cursedEnergy.put("Gojo Satoru", 9999);
cursedEnergy.put("Itadori Yuji", 500);
cursedEnergy.put("Fushiguro Megumi", 400);

System.out.println(cursedEnergy.get("Gojo Satoru"));     // 9999
System.out.println(cursedEnergy.containsKey("Sukuna"));  // false

For ArrayList, see ArrayList.add() / get(). For HashMap, see HashMap.put() / get().

Stream API

The Stream API (Java 8 and later) provides a way to process collections using a chain of filter, transform, and aggregate operations.

import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

List<String> members = Arrays.asList(
    "Gojo Satoru", "Itadori Yuji", "Fushiguro Megumi",
    "Kugisaki Nobara", "Ryomen Sukuna"
);

// Keep names longer than 12 characters, then convert to uppercase
List<String> result = members.stream()
    .filter(name -> name.length() > 12)
    .map(String::toUpperCase)
    .collect(Collectors.toList());

System.out.println(result);
// [FUSHIGURO MEGUMI, KUGISAKI NOBARA, RYOMEN SUKUNA]

For more on the Stream API, see stream().filter() / map().

Exception Handling

Exception handling describes what to do when an error occurs during program execution. Java uses try-catch-finally.

try {
    // Code that might throw an exception
    int result = 10 / 0;
} catch (ArithmeticException e) {
    // Runs if an exception is thrown
    System.out.println("Error: " + e.getMessage()); // Error: / by zero
} finally {
    // Always runs, regardless of whether an exception occurred
    System.out.println("Done.");
}

For resources that must be closed after use (files, database connections, etc.), use try-with-resources.

import java.io.*;

// close() is called automatically when the try block ends
try (BufferedReader reader = new BufferedReader(new FileReader("data.txt"))) {
    String line = reader.readLine();
    System.out.println(line);
} catch (IOException e) {
    System.out.println("Read error: " + e.getMessage());
}

For more on exception handling, see try / catch / finally.

File I/O

From Java 11 onward, the Files class makes reading and writing files concise.

import java.io.IOException;
import java.nio.file.*;

// Write to a file (overwrites existing content)
try {
    Files.writeString(Path.of("output.txt"), "Itadori Yuji, cursed energy: 9999");
    System.out.println("Write complete.");
} catch (IOException e) {
    System.out.println("Error: " + e.getMessage());
}

// Read from a file
try {
    String content = Files.readString(Path.of("output.txt"));
    System.out.println(content); // Itadori Yuji, cursed energy: 9999
} catch (IOException e) {
    System.out.println("Error: " + e.getMessage());
}

For file I/O, see Files.writeString() and Files.readString().

Generics

Generics provide a way to parameterize types. The same logic can be used safely with different types without duplicating code.

// <T> is a type parameter — the caller specifies the actual type
class Box<T> {
    T value;

    Box(T value) {
        this.value = value;
    }

    T get() {
        return value;
    }
}

// A Box for String
Box<String> nameBox = new Box<>("Fushiguro Megumi");
System.out.println(nameBox.get()); // Fushiguro Megumi

// A Box for Integer
Box<Integer> powerBox = new Box<>(8500);
System.out.println(powerBox.get()); // 8500

The <> syntax in ArrayList<String> and HashMap<String, Integer> is generics in use. For more, see Generics.

Interfaces

An interface defines a set of methods that a class must implement. A class uses implements to declare that it satisfies the interface contract.

// Interface definition
interface Curseable {
    // Any class implementing this interface must provide these methods
    void activateCurse();
    String getName();
}

// Class implementing the interface
class Sorcerer implements Curseable {
    private String name;

    Sorcerer(String name) {
        this.name = name;
    }

    @Override
    public void activateCurse() {
        System.out.println(name + " used a cursed technique!");
    }

    @Override
    public String getName() {
        return name;
    }
}

Curseable kugisaki = new Sorcerer("Kugisaki Nobara");
kugisaki.activateCurse(); // Kugisaki Nobara used a cursed technique!

Using interfaces allows you to write code that depends on a contract rather than a concrete implementation. For more, see interface / Abstract Class.

Asynchronous Processing — CompletableFuture

From Java 8 onward, CompletableFuture provides a way to write asynchronous code. Tasks run on separate threads in parallel, and follow-up steps can be chained to run after completion.

import java.util.concurrent.CompletableFuture;

// Run a task asynchronously (simulates an API call)
CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    // Heavy work runs on a separate thread
    return "Ryomen Sukuna";
});

// Chain steps to run after the result is ready
future.thenApply(name -> "Cursed King: " + name)
      .thenAccept(System.out::println); // Cursed King: Ryomen Sukuna

// Block until the result is available and retrieve it
String result = future.join();
System.out.println(result); // Ryomen Sukuna

For more on CompletableFuture, see CompletableFuture.

Common Errors and How to Fix Them

NullPointerException

The most frequently encountered error. It occurs when a method is called on a null variable.

String name = null;
System.out.println(name.length()); // NullPointerException!
// Fix: check for null before calling the method
String name = null;
if (name != null) {
    System.out.println(name.length());
} else {
    System.out.println("name is null");
}

ClassCastException

Occurs when an object is cast to an incompatible type.

Object obj = "Gojo Satoru";
Integer num = (Integer) obj; // ClassCastException!
// Fix: check the type with instanceof before casting
Object obj = "Gojo Satoru";
if (obj instanceof Integer) {
    Integer num = (Integer) obj;
} else {
    System.out.println("Not an Integer: " + obj.getClass().getName());
}

ArrayIndexOutOfBoundsException

Occurs when accessing an array at an index outside its bounds.

int[] scores = {100, 85, 92};
System.out.println(scores[3]); // ArrayIndexOutOfBoundsException!
// Fix: check the array length before accessing
int[] scores = {100, 85, 92};
int index = 3;
if (index < scores.length) {
    System.out.println(scores[index]);
} else {
    System.out.println("Index out of bounds");
}

Comparing Strings with ==

Using == on String compares references (memory addresses), not content.

String a = new String("Gojo Satoru");
String b = new String("Gojo Satoru");
System.out.println(a == b);       // false (different references)
System.out.println(a.equals(b));  // true (same content)

Always use .equals() to compare string content.

Recommended Learning Order

A suggested path through the Java dictionary. There is no need to memorize everything at once — look up each page when you need it.

StepTopicPages
1 Setup and running files Setup

Running .java Files
2 Variables, types, and strings String.length() / charAt()

split() / join()
3 Classes and object-oriented programming Class Definition / Constructor

extends / Override
4 Collections ArrayList

HashMap
5 Exception handling try / catch / finally
6 Stream API and lambda expressions stream().filter() / map()

Lambda Expressions
7 File I/O Files.writeString()

Files.readString()
8 Generics and interfaces Generics

interface / Abstract Class
9 Asynchronous processing CompletableFuture

Summary

The Big Picture

Java source code is written in .java files and compiled by javac into bytecode (.class files). Bytecode runs on the JVM, so the same program runs on any OS where a JVM is installed (Write Once, Run Anywhere).

Java is a statically typed object-oriented language. Type mismatches are caught at compile time. Classes hold fields and methods, and instances are created with new.

Key Features at a Glance

  • Variables and types → Static typing. Primitive types (int, boolean, etc.) and reference types (String, etc.).
  • Classes and objects → Defined with class, instantiated with new. Inheritance via extends.
  • Collections → ArrayList (dynamic list) / HashMap (key-value map).
  • Stream API → .stream().filter().map().collect() for declarative collection processing.
  • Exception handling → try-catch-finally / try-with-resources.
  • File I/O → Files.writeString() / Files.readString() (Java 11 and later).
  • Generics → <T> parameterizes types for type-safe reuse.
  • Interfaces → interface defines a method contract; implements fulfills it.
  • Asynchronous processing → CompletableFuture for parallel tasks and chained callbacks (Java 8 and later).

Common Errors

  • NullPointerException → A method was called on a null variable. Add a null check first.
  • ClassCastException → Cast to an incompatible type. Use instanceof before casting.
  • ArrayIndexOutOfBoundsException → Accessed an array beyond its length. Check .length first.
  • String comparison with == → Compares references, not content. Use .equals() instead.

If you find any errors or copyright issues, please .