Problem Description
Given an array nums and an integer target, an infinite array is generated by repeating nums indefinitely. Find the length of the shortest contiguous subarray (which might span several copies of nums) that sums exactly to target. Return -1 if no such subarray exists.
Key Insights
- The infinite array is simply repeated cycles of nums.
- Since nums contains only positive integers, sums in any contiguous range are strictly increasing as more elements are added.
- Any valid subarray can either lie completely within one or two cycles, or span multiple cycles.
- A window that “wraps around” (ends in a later copy than it started) can be decomposed into a suffix from one cycle, a number of full cycles, and a prefix from the next cycle.
- Precomputing prefix sums for one cycle allows us to use binary search (since the prefix sums are strictly increasing) to check if a given partial sum exists.
Space and Time Complexity
Time Complexity: O(n log n), where n is the length of nums (we iterate over each starting index and do a binary search over the prefix array). Space Complexity: O(n) for storing the prefix sums.
Solution
We can solve the problem by first precomputing the prefix sums for one cycle of nums. For a given start index i in [0,n-1], we consider two cases:
-
The desired subarray lies within the same cycle.
- Compute the sum from index i to some index j in the same cycle.
- Since the prefix sums are strictly increasing, we can binary search for j such that (pre[j] - pre[i]) equals target.
-
The desired subarray spans multiple cycles.
- Compute the sum from i to the end of the cycle (suffix).
- Let rem = target - (sum of suffix). Since the numbers are positive, rem > 0.
- Notice that additional whole cycles sum to totalSum. Write rem = m*totalSum + x, where 0 <= x <= totalSum.
- For the subarray to sum exactly to target, x must equal the sum of a prefix of nums (that is, it must appear in the precomputed prefix array). If x is found, the total length is (n - i) + m*n + (prefix length corresponding to x).
- Specially, if x is zero (i.e. rem is exactly m*totalSum), no extra part is needed.
We iterate over all starting positions and keep track of the minimum candidate length. If no candidate is found, return -1.