Non-Primitive Data types in Java
We know that data types in Java are categorized into primitive and non-primitive data types.
Primitive data types are those data types that are used by programmers when creating variables in their programs. They are used to store a single value (or entity).
For example, an int type can store only one integer value, and a boolean type can store only one value — either true or false. There are eight primitive data types in Java. They are boolean, char, byte, short, int, long, float, and double.
Now, we will learn about another category of data types supported by Java, known as non-primitive data types (or reference/advanced data types).
Non-primitive Data types (Reference Data types) in Java
Non-primitive data types are created by programmers. They are not predefined in Java like primitive data types. These data types are used to store a group of values or several values.
For example,
- An array can store a group of values of the same type.
- Similarly, a class can hold variables and methods together.
- A string can store the sequence of characters.
Therefore, these data types are known as advanced data types in Java. They allow you to represent complex entities and relationships.
How Non-Primitive Data Types Work in Memory?
When you define a variable of non-primitive data types, it references a memory location where the actual data (object) is stored in the heap memory. In other words, it holds a reference to the memory location where the object resides.
So, a reference variable points to an object in heap memory.
- Stack Memory: Holds the reference variable (the pointer).
- Heap Memory: Holds the actual object or data.
Hence, a non-primitive data type variable is also called referenced data type, or simply an object reference variable in Java because they reference the memory address of the object. For example:
String name = "Java";In this example,
- The object reference variable (name) itself resides in the stack memory.
- While, the object (Java) to which it points always resides in the heap memory.
- The stack holds a pointer (reference) to the object in the heap. In other words, the reference variable name points to the location of the “Java” object in the heap.
Note:
In Java programming, all non-primitive data types are simply called objects which are created by instantiating classes.
How to Declare Non-Primitive Data Types in Java?
In Java, non-primitive (reference) data types are declared in a way similar to primitive types, but they store references to objects, not actual values.
Declaration of Primitive Data Type
In a primitive data type, variable directly stores the value. For example,
int p = 100;Here,
- p is an int data type that stores a single integer value 100.
Declaration of Reference Data Type (Object Reference Variable)
In reference data types, an object reference variable ( or simply called reference variable) is declared just like we declare a primitive variable.
School sc;Here,
- School is the name of a class
- “sc” is the name of a reference variable that can store the address of an object of type school.
At this point, no object has been created yet because only sc holds null by default.
Creating an Object Using new Keyword
We create an object of a class using a new keyword. For example, the following statement creates an object of a class School and assigns it to the reference variable “sc”.
sc = new School();Where,
- School ➞ Name of the class.
- sc ➞ Object reference variable that stores the address of an object in the computer’s memory. An object represents an instance through which we can access a member.
- School() ➞ Constructor of the class. The constructor of a class is generally used to initialize an object.
- new ➞ Special keyword that allocates the memory for the object in Java.
After this statement,
- The object of class School is created in the heap memory.
- The object reference variable “sc” resides in the stack memory and refers to the object in the heap (as shown in the below figure).
Declaring, Creating, and Initializing an Object in One Line
The declaration of an object reference variable, object creation, and initialization of the reference variable can also be done in a single line statement like this:
School sc = new School();This is the most common and recommended way to create objects in Java.
Example: Demonstrating Object Reference Variable
Let’s take a simple example in which we will get the object’s address as output stored in the object reference variable on the stack memory.
package scientecheasy;
public class School
{
// Declaration of an instance variable (Non-primitive type).
String name = "RSVM";
public static void main(String[] args)
{
// Creating an object of the class.
School sc = new School(); // sc is a non-primitive data type (object reference variable).
// Print the address of the memory location of the object.
System.out.println(sc);
// We cannot access instance variable directly.
// Accessing the instance variable by using reference variable "sc" which is created above.
System.out.println(sc.name);
}
}Output:
School@1db9742 RSVM
In this example,
- School@1db9742 → This represents the memory address (hashcode) of the object in the heap, referenced by sc.
- RSVM → The value of the instance variable name accessed through the reference variable sc.
Thus, sc is an object reference variable that lives on the stack, while the School object it refers to lives on the heap.
Memory Allocation of Object and Object Reference Variable in Java
From the above example, you have understood that in Java, a variable whose type is a class, does not actually hold an object. Actually, it holds the memory location of an object that exists elsewhere in memory.
The object itself is stored elsewhere. In the conceptual diagram below, you can see the memory location of object and object reference variable of the above example program.
As shown in the above figure, the object reference variable ‘sc’ contains an address ‘1db9742’ which is the address of memory location of an object on the heap. On this memory address, the object’s data is stored inside the heap memory.
So, when we say we “create an object”, it means we are allocating memory in the heap to store that object’s data. In simple words, creating an object means storing data in memory. So, the reference variable “sc” does not contain the object. It refers to an object.
Types of Non-Primitive Data Types in Java
There are five types of non primitive data types in Java. They are as follows:
- Class
- Object
- String
- Array
- Interface
1. Class and Object
Every class in Java is data type and is also considered as user-defined data types because a programmer creates a class.
- A class acts as a blueprint for creating objects.
- An object is an instance of a class that occupies memory and allows you to access class members (variables and methods).
For more details, read this tutorial: Class and objects in Java.
2. String
A string in Java represents a sequence of characters like India, ABC123, etc. It is a non-primitive data type and actually a class in the java.lang package.
The simplest way to create a string object is by storing a sequence of characters into a string type variable like this:
String str = "Universe";
Here,
- str is a reference variable of type String.
- It stores the address of the “Universe” object in the heap memory.
For more details, Read this: String in Java
3. Array
An array in Java is an object which is used to store multiple variables of the same type. These variables can be primitive or non-primitive data types.
The example of declaring an array variable of primitive data type int is as follows:
int [ ] scores;The example of declaring an array variable of non-primitive data type is
Student [ ] students; // Student is a name of class.For more details, Read this: Arrays in Java
4. Interface
An interface is declared like a class, but the only difference is that it contains only constants (final variables) and abstract method declarations. It defines a contract that implementing classes must follow. An interface is, therefore, a fully abstract class.
For example:
interface Animal {
void sound();
}Here, you learned about just basic knowledge of non primitive data types in Java. You will get more knowledge in further tutorials.
Difference between Primitive and Non-primitive Data types in Java
1. Primitive data types are predefined in Java, whereas non primitive data types are created by programmers. They are not predefined in Java.
2. In primitive data type, variables can store only one value at a time. On the other hand, in non-primitive data type, we can store multiple values either the same type or different type or both.
3. All the data for primitive type variables are stored on the stack, whereas, for reference types, the stack holds a pointer to the object on the heap.
4. In Java, primitive types begin with lowercase letters. Examples include int, double, float, boolean, char, short, long, and byte. On the other hand, non-primitive types typically begin with an uppercase letter. Examples include String, Integer, Double, ArrayList, Car, etc.
5. The size of each primitive type is fixed and predefined. For instance, an int is always 32 bits, a double is always 64 bits, and so forth. On the other hand, references to non-primitive objects are of the same size.
Key Points about Non-Primitive Data Types in Java
- Class, object, array, string, and interface are called non-primitive data types in Java. These data types are not predefined in Java programming. They are created by programmers.
- Non-primitive data types are used to store a group of values or complex data structures in Java programming.
- When you define a variable of non-primitive data type, it references a memory location where data is stored in heap memory. Therefore, it is also known as a reference data type in Java.
- Passing a value of non primitive data type to a method refers to actually passing an address of that object where data is stored.
- Objects created of non primitive data types are allocated in the heap memory. Java uses an automatic garbage collection mechanism to manage memory in the heap.
- The default value of any reference type variable in Java is null if they are not explicitly initialized. The null value means that the variable currently references no object in the heap memory.






