Every day a Leetcode
题目来源:2967. 使数组成为等数数组的最小代价
解法1:贪心
题目中要求将数组变成等数数组(数组中的所有元素都等于一个小于 109 的回文数)。因此,我们需要找到一个小于 109 的回文数,使得将数组中所有元素变成这个数的代价最小。
基于贪心的思想,我们可以从中位数开始,向左查找第一个回文数 left,向右查找第一个回文数 right,然后取两者中总代价的较小值作为答案。
代码:
/*
* @lc app=leetcode.cn id=2967 lang=cpp
*
* [2967] 使数组成为等数数组的最小代价
*/
// @lc code=start
class Solution
{
public:
long long minimumCost(vector<int> &nums)
{
// 特判
if (nums.empty())
return 0LL;
int n = nums.size();
sort(nums.begin(), nums.end());
int left = nums[n / 2];
while (left > 0 && isPalindrome(left) == false)
left--;
int right = nums[n / 2];
while (right <= 1e9 && isPalindrome(right) == false)
right++;
return min(calCost(nums, left), calCost(nums, right));
}
// 辅函数 - 判断 x 是不是回文数
bool isPalindrome(int x)
{
string s = to_string(x);
return s == string(s.rbegin(), s.rend());
}
// 辅函数 - 计算将数组 nums 的所有元素全部变成 x 的代价
long long calCost(vector<int> &nums, int x)
{
long long cost = 0;
for (int &num : nums)
cost += abs(num - x);
return cost;
}
};
// @lc code=end
结果:
复杂度分析:
时间复杂度:O(nlogn),其中 n 是数组 nums 的长度。
空间复杂度:O(1)。