通过组合两个元素或拆分一个元素来最大化 Array 的不同元素
给定一个长度为N的数组arr[] ,任务是通过执行以下任一操作来最大化数组中不同元素的数量,任意次数:
- 对于索引i (0 ≤ i < N),将arr[i]替换为a和b使得arr[i] = a + b 。
- 对于两个索引 i (0 ≤ i < N) 和n (0 ≤ n < N),将arr[n]替换为 ( arr[i] + arr[n] )。从数组中弹出arr[i] 。
例子:
Input: arr[] = {1, 4, 2, 8}, N = 4
Output: 5
Explanation: arr[3] can be split into [3, 5] to form arr [] = {1, 4, 2, 3, 5}.
There is no other way to split this into more elements.
Input: arr[] = {1, 1, 4, 3}, N = 4
Output: 3
Explanation: No operations can be performed to increase the number of distinct elements.
方法:这个问题可以基于以下观察:
Using the second operation, the entire arr[] can be reduced to 1 element, such that arr[0] = sum(arr[]). Now, the array sum can be partitioned into maximum number of unique parts get maximum unique elements.
按照以下步骤实施观察:
- 遍历数组并找到数组元素的总和(比如sum )。
- 现在要获得 sum 的最大唯一分区,最好为每个部分分配尽可能低的值。
- 因此,从i = 1循环,只要sum > 0 :
- 从sum中减去i ,然后将i加 1。
- 唯一元素的总数是i – 1,因为在循环的最后一次迭代中有一个额外的增量。
下面是上述方法的实现。
C++
// C++ code to implement the above approach
#include
using namespace std;
// Function to calculate the maximum possible
// number of unique elements
int maxUniqueElems(int* Arr, int L)
{
// Initializng sums variable
int sums = 0;
// Calculating sum of array
for (int j = 0; j < L; j++)
sums += Arr[j];
// Initializing i to count total number of
// distint elements
int i = 1;
// Looping till sums becomes 0
while (sums > 0) {
// Subtracting i from sums and
// incrementing i
sums -= i;
i++;
}
// Returning the result
return i - 1;
}
// Driver code
int main()
{
int arr[] = { 1, 4, 2, 8 };
int N = 4;
// Function call
cout << maxUniqueElems(arr, N);
return 0;
}
5
时间复杂度: O(max(N, sqrt(S))) 其中 S 是数组的总和
辅助空间: O(1)