Any positive divisor of a natural number x that is strictly less than x is called a proper divisor of x. For example, 2 is a proper divisor of 4, while 6 is not a proper divisor of 6.
You are allowed to perform an operation any number of times on nums, where in each operation you select any one element from nums and divide it by its greatestproper divisor.
Return the minimum number of operations required to make the array
non-decreasing.
If it is not possible to make the array non-decreasing using any number of operations, return -1.
To make the array non-decreasing, we need to ensure every element is less than or equal to the next. We process from right to left, dividing elements by their greatest proper divisor only when necessary. If at any point we cannot make an element small enough, it’s impossible.
For each element, if it is greater than the next, repeatedly divide it by its greatest proper divisor until it becomes less than or equal to the next element.
Count each division as an operation.
If an element becomes 1 and is still greater than the next, return -1.
classSolution {
public:int minOperations(vector<int>& nums) {
int ans =0;
for (int i = nums.size() -2; i >=0; --i) {
int cur = nums[i];
int nxt = nums[i+1];
int ops =0;
while (cur > nxt) {
if (cur ==1) return-1;
int div = cur /2;
for (int d =2; d * d <= cur; ++d) {
if (cur % d ==0) div = max(div, cur / d);
}
cur = div;
++ops;
}
ans += ops;
nums[i] = cur;
}
return ans;
}
};
classSolution {
publicintminOperations(int[] nums) {
int ans = 0;
for (int i = nums.length- 2; i >= 0; i--) {
int cur = nums[i];
int nxt = nums[i+1];
int ops = 0;
while (cur > nxt) {
if (cur == 1) return-1;
int div = cur / 2;
for (int d = 2; d * d <= cur; d++) {
if (cur % d == 0) div = Math.max(div, cur / d);
}
cur = div;
ops++;
}
ans += ops;
nums[i]= cur;
}
return ans;
}
}
classSolution {
funminOperations(nums: IntArray): Int {
var ans = 0for (i in nums.size - 2 downTo 0) {
var cur = nums[i]
val nxt = nums[i+1]
var ops = 0while (cur > nxt) {
if (cur ==1) return -1var div = cur / 2for (d in2..Math.sqrt(cur.toDouble()).toInt()) {
if (cur % d ==0) div = maxOf(div, cur / d)
}
cur = div
ops++ }
ans += ops
nums[i] = cur
}
return ans
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
defmin_operations(nums: list[int]) -> int:
ans =0for i in range(len(nums) -2, -1, -1):
cur = nums[i]
nxt = nums[i+1]
ops =0while cur > nxt:
if cur ==1:
return-1 div = cur //2for d in range(2, int(cur **0.5) +1):
if cur % d ==0:
div = max(div, cur // d)
cur = div
ops +=1 ans += ops
nums[i] = cur
return ans
impl Solution {
pubfnmin_operations(nums: &mut Vec<i32>) -> i32 {
letmut ans =0;
for i in (0..nums.len()-1).rev() {
letmut cur = nums[i];
let nxt = nums[i+1];
letmut ops =0;
while cur > nxt {
if cur ==1 { return-1; }
letmut div = cur /2;
letmut d =2;
while d * d <= cur {
if cur % d ==0 {
div = div.max(cur / d);
}
d +=1;
}
cur = div;
ops +=1;
}
ans += ops;
nums[i] = cur;
}
ans
}
}
⏰ Time complexity: O(n * sqrt(m)), where n is the length of nums and m is the maximum value in nums. For each element, we may need to check all divisors up to sqrt(m).
🧺 Space complexity: O(1), only a few variables are used for tracking the answer.