Type casting is one of the most fundamental concepts in Java. Every Java developer encounters it while working with variables, arithmetic operations, method calls, and object-oriented programming.
Java supports two types of type casting:
- Implicit Type Casting (Automatic/Widening)
- Explicit Type Casting (Manual/Narrowing)
In this article, we'll understand both with simple examples, binary explanations, common interview questions, and memory tricks.
What is Type Casting?
Type casting is the process of converting a value from one data type to another.
Java performs this conversion in two ways:
- Implicit Type Casting (Automatic)
- Explicit Type Casting (Manual)
1. Implicit Type Casting (Automatic)
Implicit type casting happens automatically when a value of a smaller data type is assigned to a larger data type.
Since the destination type can safely hold the value, Java performs the conversion automatically.
It is also known as:
- Widening Conversion
- Widening Casting
- Upcasting (for primitive types, widening)
Characteristics
| Property | Description |
|---|---|
| Performed by | Compiler |
| Direction | Smaller → Larger |
| Cast required? | ❌ No |
| Data loss | ❌ Never |
| Also called | Widening Conversion |
Widening Conversion Hierarchy
byte
↓
short char
↘ ↙
int
↓
long
↓
float
↓
double
Note: Although
charandshortare both 2 bytes, Java does not allow implicit conversion between them. Both are promoted toint.
Example 1: char → int
int x = 'a';
System.out.println(x);
Output
97
Why?
The Unicode value of 'a' is 97, so Java automatically converts the character into its integer representation.
Example 2: int → double
double salary = 10;
System.out.println(salary);
Output
10.0
The compiler automatically converts the integer into a double.
Example 3: int → long
long population = 100;
System.out.println(population);
Output
100
No cast is required because long can safely store every int value.
2. Explicit Type Casting (Manual)
Explicit casting is required when assigning a value from a larger data type to a smaller data type.
Since information may be lost, Java requires the programmer to perform the conversion manually.
It is also called:
- Narrowing Conversion
- Narrowing Casting
- Downcasting (for primitive types, narrowing)
Characteristics
| Property | Description |
|---|---|
| Performed by | Programmer |
| Direction | Larger → Smaller |
| Cast required? | ✅ Yes |
| Data loss | Possible |
| Also called | Narrowing Conversion |
Syntax
smallerType variable = (smallerType) biggerValue;
Example Without Casting
int x = 130;
byte b = x;
Compiler Error
possible lossy conversion from int to byte
Java refuses the assignment because a byte cannot store every integer value safely.
Example With Explicit Casting
int x = 130;
byte b = (byte) x;
System.out.println(b);
Output
-126
The program compiles successfully, but the value changes because data is lost during narrowing.
Why Does (byte)130 Become -126?
An int occupies 32 bits, while a byte occupies only 8 bits.
Step 1
Binary representation of 130 (32-bit integer)
00000000 00000000 00000000 10000010
Step 2
When converting to byte, Java keeps only the last 8 bits.
10000010
The remaining 24 bits are discarded.
Step 3
The leftmost bit is now 1, so Java treats it as a negative number.
Take the two's complement to find the magnitude.
Flip bits
01111101
Add 1
01111110
126
Therefore,
(byte)130 = -126
Another Example
int x = 150;
short s = (short) x;
byte b = (byte) x;
System.out.println(s);
System.out.println(b);
Output
150
-106
Why?
-
shortcan store 150. -
bytecannot, so overflow occurs.
Rule: Higher → Lower Keeps Only the Least Significant Bits
When narrowing,
- Higher-order (most significant) bits are discarded.
- Only the least significant bits remain.
This is why overflow occurs.
Floating Point to Integral Conversion
When converting a floating-point value to an integral type:
- The decimal part is removed.
- Java truncates, not rounds.
Example
double d = 130.456;
int x = (int) d;
System.out.println(x);
Output
130
The digits after the decimal point are simply discarded.
Java Does NOT Round
System.out.println((int)130.999);
Output
130
Not
131
Floating Point + Narrowing
double d = 130.456;
byte b = (byte) d;
System.out.println(b);
Output
-126
Two things happen:
- Decimal portion removed
130
- Integer narrowed to byte
(byte)130
↓
-126
Implicit vs Explicit Casting
| Feature | Implicit (Widening) | Explicit (Narrowing) |
|---|---|---|
| Direction | Smaller → Larger | Larger → Smaller |
| Cast required | ❌ No | ✅ Yes |
| Performed by | Compiler | Programmer |
| Data loss | Never | Possible |
| Example | double d = 10; |
byte b = (byte)130; |
Visual Representation
Smaller Types
byte
↓
short char
↘ ↙
int
↓
long
↓
float
↓
double
↑ Widening (Implicit)
↓ Narrowing (Explicit)
Quick Examples
| Statement | Result | Casting |
|---|---|---|
int x = 'a'; |
97 | Implicit |
double d = 10; |
10.0 | Implicit |
long l = 100; |
100 | Implicit |
byte b = 130; |
Compile Error | Not Allowed |
byte b = (byte)130; |
-126 | Explicit |
int x = (int)130.456; |
130 | Explicit |
byte b = (byte)130.456; |
-126 | Explicit |
Bonus: Object Type Casting
The same widening and narrowing concepts apply to objects.
Upcasting (Automatic)
Object obj = new String("Rajesh");
A child object can always be stored in a parent reference.
No cast is required.
Downcasting (Manual)
Object obj = new String("Rajesh");
String name = (String) obj;
A cast is required because Java cannot guarantee that every Object is actually a String.
Safe Downcasting
Before downcasting, use instanceof.
Object obj = new String("Rajesh");
if (obj instanceof String) {
String name = (String) obj;
System.out.println(name);
}
This avoids ClassCastException.
Interview Questions
Which casting is automatic?
Implicit (Widening)
Which casting requires the cast operator?
Explicit (Narrowing)
Does widening ever lose data?
No.
Does narrowing lose data?
It may.
What happens when converting a floating-point number to an integer?
The decimal part is truncated, not rounded.
Why does (byte)130 become -126?
Because only the last 8 bits are retained, resulting in overflow.
Can char be assigned to int?
Yes.
int x = 'a';
Output
97
Can short be assigned to char implicitly?
No.
Both are 2 bytes, but they are different data types.
Memory Tricks 🧠
Implicit Casting
Going UP is free.
Smaller → Larger
Compiler does it automatically.
Explicit Casting
Going DOWN needs a cast and may lose data.
Larger → Smaller
You perform the conversion manually.
Floating Point → Integer
Decimals are chopped off, not rounded.
Narrowing
Only the least significant bits survive.
Key Takeaways
- Java supports implicit (widening) and explicit (narrowing) type casting.
- Implicit casting happens automatically when converting from a smaller type to a larger type.
- Explicit casting is required when converting from a larger type to a smaller type because data loss may occur.
- During narrowing, Java keeps only the least significant bits, which can lead to overflow.
- Converting floating-point values to integral types removes the decimal portion through truncation.
- The same widening and narrowing concepts also apply to object references, where downcasting should be performed carefully using
instanceof.
Happy Coding!
Top comments (0)