Java Programs›Arrays›Reverse an Array

Reverse an Array in Java

beginner·  Arrays  ·  Array Manipulation

Problem

Reversing an array means rearranging its elements so the last becomes first and the first becomes last.

Given an array of integers, reverse the order of its elements.

Input
[10, 20, 30, 40, 50]
Output
[50, 40, 30, 20, 10]

Java Program

Java
import java.util.Arrays; public class ReverseArray { public static void main(String[] args) { int[] arr = {10, 20, 30, 40, 50}; int left = 0, right = arr.length - 1; // Swap elements from both ends, moving inward while (left < right) { int temp = arr[left]; arr[left] = arr[right]; arr[right] = temp; left++; right--; } System.out.println(Arrays.toString(arr)); } }

Output

[50, 40, 30, 20, 10]

Core Logic

Two pointers starting at opposite ends and swapping as they move inward reverse the array without needing any extra memory.

How It Works
  1. 1Two pointers, left and right, start at index 0 and arr.length - 1.
  2. 2At each step, the elements at left and right are swapped using a temp variable.
  3. 3left increments and right decrements after every swap, moving both pointers toward the middle.
  4. 4The loop stops once left meets or crosses right, meaning every pair has been swapped exactly once.
For [10, 20, 30, 40, 50], swapping 10↔50 then 20↔40 leaves 30 untouched in the middle — producing [50, 40, 30, 20, 10].
💡

Key Point: Reversing in place with two pointers uses O(1) extra space, unlike building a brand-new reversed array.

Complexity
Time Complexity: O(n)Space Complexity: O(1)

Why: Each element is visited once as the two pointers move inward, and the swap happens in place using only a temp variable.

Key Concepts

two-pointer techniqueArrays.toString()

Approach 2: Recursion

Java
import java.util.Arrays; public class ReverseArrayRecursive { static void reverse(int[] arr, int left, int right) { // Base case: pointers met or crossed, every pair swapped if (left >= right) return; int temp = arr[left]; arr[left] = arr[right]; arr[right] = temp; // Recurse inward for the next pair reverse(arr, left + 1, right - 1); } public static void main(String[] args) { int[] arr = {10, 20, 30, 40, 50}; reverse(arr, 0, arr.length - 1); System.out.println(Arrays.toString(arr)); } }

Output

[50, 40, 30, 20, 10]

Core Logic

The same swap can be driven by recursion instead of a loop — each call handles one pair and passes a narrower range to the next.

How It Works
  1. 1The base case if (left >= right) return; stops the recursion once the pointers meet or cross.
  2. 2Each call swaps arr[left] and arr[right] using a temp variable, exactly like the iterative version's loop body.
  3. 3It then recurses with reverse(arr, left + 1, right - 1), narrowing the window by one on each side.
  4. 4Because the array is mutated in place, no value needs to be returned — the recursion is purely for control flow.
reverse(arr, 0, 4) swaps 10↔50, then recurses into reverse(arr, 1, 3) which swaps 20↔40, then reverse(arr, 2, 2) hits the base case.
💡

Key Point: Same O(1) extra space as the loop version, since the swaps still happen in place — recursion here is just a different way to express the same iteration, not a performance improvement.

Complexity
Time Complexity: O(n)Space Complexity: O(1)

Why: The swaps happen in place using the same temp variable as the loop version, so no extra data structures are allocated as the recursion unwinds.

Key Concepts

recursionin-place swapbase case

Approach 3: Java 8

Java
import java.util.Arrays; import java.util.stream.IntStream; public class ReverseArrayStream { public static void main(String[] args) { int[] arr = {10, 20, 30, 40, 50}; // Maps each index to the element at its mirrored position from the end int[] reversed = IntStream.range(0, arr.length) .map(i -> arr[arr.length - 1 - i]) .toArray(); System.out.println(Arrays.toString(reversed)); } }

Output

[50, 40, 30, 20, 10]

Core Logic

A stream can build the reversed array directly — map each index to its mirrored position and collect the results into a brand-new array.

How It Works
  1. 1IntStream.range(0, arr.length) generates every valid index from 0 to arr.length - 1.
  2. 2.map(i -> arr[arr.length - 1 - i]) maps each index to the element sitting at its mirrored position from the end.
  3. 3.toArray() collects the mapped values into a brand-new int[], built in reversed order.
For [10, 20, 30, 40, 50], index 0 maps to arr[4] = 50, index 1 maps to arr[3] = 40, and so on, producing [50, 40, 30, 20, 10].
💡

Key Point: Unlike the two-pointer swap, this builds a brand-new array instead of reversing in place — trading the O(1) extra space of the loop version for a more declarative, side-effect-free expression.

Complexity
Time Complexity: O(n)Space Complexity: O(n)

Why: The stream maps every index to its mirrored element and collects the results into a brand-new int[], so the output array itself accounts for the extra space.

Key Concepts

StreamIntStreamtoArray()

Interview Questions

Why does the loop stop at the middle?

Each swap fixes two positions at once, one from each end. Continuing past the middle would swap every pair back again and leave the array unchanged.

How do you reverse an array with built-in methods?

For an object array such as Integer[], Collections.reverse(Arrays.asList(arr)) reverses it in place. It doesn't work on a primitive int[], because Arrays.asList treats the whole int[] as a single element.

What's the time and space complexity of the two-pointer reverse?

O(n) time and O(1) extra space — each element is moved once and only one temporary variable is needed.

Learn the Concept

Related Programs