【LeetCode每日一题】1224.最大相等频率

143 阅读2分钟

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第18天,点击查看活动详情

【LeetCode每日一题】1224.最大相等频率

题目链接:leetcode.cn/problems/ma…

题目难度:困难

题意

给你一个正整数数组 nums,请你帮忙从该数组中找出能满足下面要求的 最长 前缀,并返回该前缀的长度:

从前缀中 恰好删除一个 元素后,剩下每个数字的出现次数都相同。 如果删除这个元素后没有剩余元素存在,仍可认为每个数字都具有相同的出现次数(也就是 0 次)。

示例1:

输入:nums = [2,2,1,1,5,3,3,5]
输出:7
解释:对于长度为 7 的子数组 [2,2,1,1,5,3,3],如果我们从中删去 nums[4] = 5,就可以得到 [2,2,1,1,3,3],里面每个数字都出现了两次。

示例2:

输入:nums = [1,1,1,2,2,2,3,3,3,4,4,4,5]
输出:13

提示:

  • 2<=nums.length<=1052 <= nums.length <= 10^5
  • 1<=nums[i]<=1051 <= nums[i] <= 10^5

题解:转换思维+分情况讨论

题解参考【宫水三叶】姐姐题解:题解地址

首先设置几个数据结构:

  • cnt[i]:表示数字i出现的频率
  • num_sum[i]:表示频率为i对应的不同数值有多少个
  • max_cnt:表示最大的频率

遍历整个数组,假设当前遍历位置为i,如果当前的前缀能够满足题意,则必须满足以下三种情况之一(下面出现的len=i+1len=i+1):

  1. 所有的数值出现的频率均为1(即:max_cnt=1max\_cnt=1
  2. 除某一个值外,所有的数值出现的频率为max_cnt1max\_cnt-1,同时某一个数值出现的频率为max_cnt(即:(num_sum[max_cnt1]+1)(max_cnt1)+1==lennum\_sum[max\_cnt-1]+1)*(max\_cnt-1)+1 == len,为什么num_sum[max_cnt1]num\_sum[max\_cnt-1]需要+1,因为"某个数值"-1后,频率会从max_cnt变成max_cnt-1。)
  3. 除某一个值外,其他的所有数值出现频率为max_cnt,同时某一个值出现的频率为1(即:num_sum[max_cnt]max_cnt+1==lennum\_sum[max\_cnt]*max\_cnt+1 == len

C++代码

class Solution {
public:
    int cnt[100005]; //cnt[i]:表示i出现的次数
    int num_sum[100005]; //num_sum[i]:表示频率为i对应的不同数值有多少个
    int maxEqualFreq(vector<int>& nums) {
        int n=nums.size();
        int max_cnt=0; //最大的频率
        int ans=0;
        for(int i=0;i<n;i++){
            int x=++cnt[nums[i]];
            num_sum[x]++;num_sum[x-1]--;
            int len = i+1;
            if(x>max_cnt) max_cnt=x;
            if(max_cnt == 1) ans=len;
            else if(num_sum[max_cnt]==1 && ( (num_sum[max_cnt-1]+1)*(max_cnt-1) +1 == len) ) ans=len;
            else if(num_sum[max_cnt]*max_cnt+1 == len) ans=len;
        }
        return ans;
    }
};