AlgoMaster Logo

Squares of a Sorted Array

easyFrequency4 min readUpdated June 23, 2026

Understanding the Problem

We have a sorted array that might contain negative numbers. We need to square every element and return the result in sorted order. Squaring can flip the order. For example, -4 squared is 16, which is larger than 3 squared (9), even though -4 comes before 3 in the original array.

In the original sorted array, the largest squares are at the two ends. The most negative numbers (far left) and the most positive numbers (far right) produce the biggest squares. The smallest squares are somewhere in the middle, near zero. This U-shape pattern in the squared values is what makes the two-pointer technique work here.

Key Constraints:

  • -10^4 <= nums[i] <= 10^4 → Squaring the max magnitude gives 10^8, which fits in a signed 32-bit integer (max about 2.1 x 10^9). No overflow concerns, so plain int is safe in every language here.
  • nums is sorted in non-decreasing order → The ordering can be exploited to avoid sorting from scratch. This is what enables the O(n) two-pointer solution below.

Approach 1: Square and Sort

Intuition

Square every element, then sort the result. This ignores the fact that the input is already sorted, but it gives a correct baseline to improve on.

Algorithm

  1. Create a new array of the same size as nums.
  2. Square each element and store it in the new array.
  3. Sort the new array.
  4. Return the sorted array.

Example Walkthrough

Input:

0
-4
1
-1
2
0
3
3
4
10
nums

After squaring each element:

0
16
1
1
2
0
3
9
4
100
squared

After sorting the squared array:

0
0
1
1
2
9
3
16
4
100
result

Code

The sort is the bottleneck, and it throws away the ordering the input already had. The next approach builds the squared result in sorted order directly, in O(n) time.

Approach 2: Two Pointers (Optimal)

Intuition

When a sorted array contains negative numbers, the largest squared values sit at the two extremes. Consider [-4, -1, 0, 3, 10]. The squares are [16, 1, 0, 9, 100]. The biggest square (100) comes from the rightmost element, the second biggest (16) from the leftmost, and the smallest squares cluster near the middle, around zero.

The squared values form a U-shape: large on both ends, small in the middle. So we can place two pointers, one at each end, and compare their squares. Whichever is bigger is the next-largest value overall, so it goes into the result. We fill the result array from the back, since the largest values are found first.

Algorithm

  1. Initialize two pointers: left at the start (index 0) and right at the end (index n-1).
  2. Create a result array of size n.
  3. Fill the result array from the back (index n-1 down to 0).
  4. At each position, compare nums[left]^2 with nums[right]^2.
  5. Place the larger square at the current position in the result.
  6. Move the corresponding pointer inward (left pointer moves right, right pointer moves left).
  7. Return the result array.

Example Walkthrough

nums
1Initialize: left=0, right=4, filling result from pos=4
0
-4
left
1
-1
2
0
3
3
4
10
right
result
1Result array empty, will fill from right to left
[_, _, _, _, _]
1/6

Code