Every Java program follows a specific structure.
Whether you're writing a simple "Hello, World!" program or a large enterprise application with thousands of classes, every Java source file follows the same basic layout.
Understanding this structure helps you organize code correctly and avoid common compile-time errors.
In this article, we'll explore:
- The structure of a Java source file
- The purpose of the
importstatement - Types of imports
- How Java resolves class names
- Common interview questions
- Best practices
What Is a Java Source File?
A Java source file is simply a file with the .java extension.
Example
Student.java
OrderService.java
Employee.java
Every Java source file contains Java source code that is compiled into bytecode (.class files).
Structure of a Java Source File
A Java source file can contain three sections, always in this order:
1. Package statement (optional)
2. Import statements (optional)
3. Class / Interface / Enum / Record declarations
Visual representation
---------------------------------
Package Statement
---------------------------------
Import Statements
---------------------------------
Class / Interface Declarations
---------------------------------
The order is important.
Changing it may result in compile-time errors.
Section 1: Package Statement
The package statement is optional.
If present, it must be the first non-comment statement in the file.
Example
package com.rajesh.learning;
We'll explore packages in detail in Part 3 of this series.
Section 2: Import Statements
Import statements tell the compiler where to find classes that belong to other packages.
Example
import java.util.ArrayList;
Without imports, we'd have to write fully qualified class names everywhere.
Section 3: Class Declarations
Finally, we define classes, interfaces, enums, or records.
Example
public class Student {
}
A source file may contain multiple classes, although only one public class is allowed per file.
A Complete Example
package com.rajesh.learning;
import java.util.ArrayList;
public class Student {
public static void main(String[] args) {
ArrayList<String> names = new ArrayList<>();
names.add("Rajesh");
System.out.println(names);
}
}
Notice the order:
- Package
- Import
- Class
Is an Empty Java File Valid?
Surprisingly, yes.
An empty source file is still a valid Java program.
It compiles successfully.
Of course, it doesn't do anything.
Why Do We Need Import Statements?
Consider the following program.
public class Student {
public static void main(String[] args) {
ArrayList<String> students = new ArrayList<>();
}
}
Compile-time error
cannot find symbol
symbol: class ArrayList
The compiler doesn't know where ArrayList is located.
Solution 1: Fully Qualified Class Name
Instead of importing the class, we can write its complete name.
public class Student {
public static void main(String[] args) {
java.util.ArrayList<String> students =
new java.util.ArrayList<>();
}
}
This works perfectly.
However, the code becomes lengthy and difficult to read.
Solution 2: Import Statement
A better approach is to import the class once.
import java.util.ArrayList;
public class Student {
public static void main(String[] args) {
ArrayList<String> students = new ArrayList<>();
}
}
Now we can use the short class name throughout the file.
Benefits of Import Statements
Imports make code:
- Shorter
- Cleaner
- Easier to read
- Easier to maintain
Types of Import Statements
Java provides two types of imports.
1. Explicit Class Import
Imports a single class.
import java.util.ArrayList;
Example
import java.util.ArrayList;
public class Student {
public static void main(String[] args) {
ArrayList<String> students = new ArrayList<>();
}
}
This is the recommended approach.
It clearly tells readers which class is being used.
2. Wildcard Import
Imports all public classes from a package.
import java.util.*;
Example
import java.util.*;
public class Student {
public static void main(String[] args) {
ArrayList<String> students = new ArrayList<>();
HashMap<Integer, String> map = new HashMap<>();
}
}
Although convenient, wildcard imports make it less obvious which classes are actually used.
Does Wildcard Import Import Subpackages?
No.
This is a common interview question.
import java.util.*;
Imports classes like:
ArrayListHashMapCollectionsScanner
But it does not import classes from subpackages.
For example,
java.util.concurrent
is not imported.
You must import it separately.
import java.util.concurrent.ConcurrentHashMap;
Fully Qualified Name vs Import
These two programs are equivalent.
Using a fully qualified name
java.util.ArrayList<String> students =
new java.util.ArrayList<>();
Using an import
import java.util.ArrayList;
ArrayList<String> students = new ArrayList<>();
If you use the fully qualified name, an import is unnecessary.
Ambiguous Imports
Consider this example.
import java.util.*;
import java.sql.*;
public class Demo {
public static void main(String[] args) {
Date today = new Date();
}
}
Compile-time error
reference to Date is ambiguous
Why?
Because Java finds two different classes:
java.util.Datejava.sql.Date
The compiler doesn't know which one you mean.
How to Resolve Ambiguity
Use the fully qualified name.
java.util.Date today = new java.util.Date();
or
java.sql.Date today =
new java.sql.Date(System.currentTimeMillis());
Another Common Example
Many beginners accidentally import both:
java.awt.List
and
java.util.List
Using
List list;
will produce an ambiguity error.
How Does Java Resolve Class Names?
When the compiler sees a class name, it searches in this order.
- Explicit imports
- Classes in the current package
- Wildcard imports
Understanding this order explains many interview questions.
Packages Imported Automatically
Every Java program automatically imports the following package.
java.lang
That's why we can write
String
System
Math
Object
Integer
without importing them.
For example,
String name = "Rajesh";
works without
import java.lang.String;
because java.lang is imported automatically.
Are Imports a Runtime Feature?
No.
Imports exist only during compilation.
They help the compiler resolve class names.
At runtime, the JVM uses the compiled bytecode.
Therefore:
- More imports may slightly increase compile-time work.
- Imports do not affect runtime performance.
Common Beginner Mistakes
Forgetting to Import a Class
ArrayList<String> list = new ArrayList<>();
Compile-time error if ArrayList isn't imported.
Assuming Wildcard Imports Include Subpackages
Incorrect
import java.util.*;
does not import
java.util.concurrent
Importing Two Classes with the Same Name
import java.sql.*;
import java.util.*;
Using
Date date;
causes an ambiguity error.
Importing Unused Classes
Modern IDEs automatically remove unused imports.
Keeping imports clean improves readability.
Interview Questions
Can a Java source file contain multiple import statements?
Yes.
There is no limit.
Can a Java source file contain multiple package statements?
No.
Only one package statement is allowed.
Does a wildcard import include subpackages?
No.
Only classes in that package are imported.
Is java.lang imported automatically?
Yes.
Every Java program imports java.lang by default.
Are imports a compile-time concept or runtime concept?
Compile-time concept.
Best Practices
- Prefer explicit imports over wildcard imports.
- Remove unused imports.
- Avoid importing classes with the same simple name.
- Use fully qualified names only when necessary.
- Let your IDE manage imports automatically.
Quick Memory Trick 🧠
Remember PIC:
- P → Package
- I → Imports
- C → Class
Always write Java source files in this order:
Package
Imports
Class
Key Takeaways
- Every Java source file follows a fixed structure.
- The order is Package → Imports → Class declarations.
- Imports make code shorter and more readable.
- Java supports explicit and wildcard imports.
- Wildcard imports do not include subpackages.
-
java.langis imported automatically. - Imports are used only during compilation.
- Ambiguous imports occur when multiple packages contain classes with the same name.
If you found this guide helpful, leave a ❤️ and follow for more beginner-friendly Java tutorials, interview questions, and practical coding examples.
Happy Coding!
Top comments (0)