Leetcode hot 100(last day)

只出现一次的数

做法一:空间复杂度O(n),时间复杂度O(n).使用哈希存储

cpp 复制代码
class Solution {
public:
    int singleNumber(vector<int>& nums) {
            unordered_set<int>mp;
            for(auto num:nums)
            {
                if(mp.find(num)!=mp.end())
                {
                    mp.erase(num);
                }
                else
                {
                    mp.insert(num);
                }
            }   
            return *mp.begin();
    }
};

做法二:空间复杂度常数级。异或即可。

cpp 复制代码
class Solution {
public:
    int singleNumber(vector<int>& nums) {
        int ans=0;
        for(int num:nums)ans^=num;
        return ans;
    }
};

多数元素

做法一:哈希表维护即可

cpp 复制代码
class Solution {
public:
    int majorityElement(vector<int>& nums) {
        unordered_map<int,int> counts;
        int majority=0,cnt=0;
        for(int num:nums)
        {
            counts[num]++;
            if(counts[num]>cnt)
            {
                majority=num;
                cnt=counts[num];
            }
        }
        return majority;
    }
};

做法二:直接返回 sort后数组中间的数字

cpp 复制代码
class Solution {
public:
    int majorityElement(vector<int>& nums) {
        sort(nums.begin(),nums.end());
        return nums[nums.size()/2];
    }
};

颜色分类

做法一:单指针,遍历两次即可

cpp 复制代码
class Solution {
public:
    void sortColors(vector<int>& nums) {
        int n=nums.size();
        int ptr=0;
        for(int i=0;i<n;i++)
        {
            if(nums[i]==0)
            {
                swap(nums[i],nums[ptr]);
                ptr++;
            }
        }
        for(int i=ptr;i<n;i++)
        {
            if(nums[i]==1)
            {
                swap(nums[i],nums[ptr]);
                ptr++;
            }
        }
    }
};

做法二:双指针,一个指针交换0,一个指针交换1。当交换0的时候,有可能这个位置已经为1了,这样1又被交换走了,而且因为i++,不会再遍历回来,所以要在p0<p1的时候,交换i和p1

cpp 复制代码
class Solution {
public:
    void sortColors(vector<int>& nums) {
        int n=nums.size();
        int p0=0,p1=0;
        for(int i=0;i<n;i++)
        {
            if(nums[i]==1)
            {
                swap(nums[i],nums[p1]);
                p1++;
            }
            else
            {
                if(nums[i]==0)
                {
                    swap(nums[i],nums[p0]);//交换后i的位置可能是1
                    if(p0<p1)swap(nums[i],nums[p1]);
                    p0++;
                    p1++;
                }
            }
        }
    }
};

做法三:也是双指针

cpp 复制代码
class Solution {
public:
    void sortColors(vector<int>& nums) {
        int n=nums.size();
        int p0=0,p2=n-1;
        for(int i=0;i<=p2;i++)
        {
            while(i<=p2&&nums[i]==2)
            {
                swap(nums[i],nums[p2--]);
            }
            if(nums[i]==0)
            {
                swap(nums[i],nums[p0++]);
            }
        }
    }
};

下一个排列

做法:首先从后往前找到第一个a[i]<a[i+1],此时[i+1,n-1]是递减的,可能是这样的 15432,那么此时,我们需要做的就是找到一个比较小数大一点的较大数,并且和较小数交换,然后我们得到25431,[i+1,n-1]还是维持递减性质,之后反转i+1,到n-1.使用reverse函数即可

cpp 复制代码
class Solution {
public:
    void nextPermutation(vector<int>& nums) {
        int i=nums.size()-2;
        while(i>=0&&nums[i]>=nums[i+1])i--;
        if(i>=0)
        {
            int j=nums.size()-1;
            while(j>=0&&nums[i]>=nums[j])j--;
            swap(nums[i],nums[j]);
        }
        reverse(nums.begin()+i+1,nums.end());
    }
};

寻找重复数

做法一:这道题可以用二分(是的,我也没有想到),假设数组是n+1=5,也就是说数字[1,4]中有重复元素,我们定义cnt[i]为数组中小于等于i元素个数,我们可以发现,当数组中重复元素只有两个的时候例如(1,2,3,3,4),cnt[1]=1,cnt[2]=2,cnt[3]=4,cnt[4]=5,设重复数字为target,[1,target-1]的cnt<=自身,[target,n-1]>自身,所以可以通过二分来寻找,时间复杂度为O(nlogn),当数组中重复元素多于2的情况,假设被替换的数字<target,[i,target-1]-1,[target,n-1]+1,所以对大于小于的性质没有影响

cpp 复制代码
class Solution {
public:
    int findDuplicate(vector<int>& nums) {
        int n=nums.size();
        int l=1,r=n-1,ans=-1;
        while(l<=r)
        {
            int mid=(l+r)>>1;
            int cnt=0;
            for(int i=0;i<n;i++)
            {
                cnt+=nums[i]<=mid;
            }
            if(cnt<=mid)
            {
                l=mid+1;
            }
            else
            {
                r=mid-1;
                ans=mid;
            }
        }
        return ans;
    }
};

做法二:快慢指针。这个有点难理解,之后再来

cpp 复制代码
class Solution {
public:
    int findDuplicate(vector<int>& nums) {
        int slow=0,fast=0;
        do
        {
            slow=nums[slow];
            fast=nums[nums[fast]];
        }while(slow!=fast);
        slow=0;
        while(slow!=fast)
        {
            slow=nums[slow];
            fast=nums[fast];
        }
        return slow;
    }
};

做法三:二进制

cpp 复制代码
class Solution {
public:
    int findDuplicate(vector<int>& nums) {
        int n=nums.size(),ans=0;
        int bit_max=31;
        while(!((n-1)>>bit_max))bit_max-=1;
        for(int bit=0;bit<=bit_max;bit++)
        {
            int x=0,y=0;
            for(int i=0;i<n;i++)
            {
                if(nums[i]&(1<<bit))
                {
                    x+=1;
                }
                if(i&(1<<bit))y+=1;
                
            }
            if(x>y)ans|=1<<bit;
        }
        return ans;
    }
};

ending!!!!但是还是需要复习,很多时候不够专心致志去解决问题,一定要细致的再看一次,加油吧。fighting~

相关推荐
爱数模的小驴1 小时前
2025 年“认证杯”数学中国数学建模网络挑战赛 C题 化工厂生产流程的预测和控制
深度学习·算法·计算机视觉
序属秋秋秋3 小时前
算法基础_数据结构【单链表 + 双链表 + 栈 + 队列 + 单调栈 + 单调队列】
c语言·数据结构·c++·算法
apcipot_rain4 小时前
【密码学——基础理论与应用】李子臣编著 第五章 序列密码 课后习题
算法·密码学
不要不开心了4 小时前
sparkcore编程算子
pytorch·分布式·算法·pygame
88号技师4 小时前
【2024年最新IEEE Trans】模糊斜率熵Fuzzy Slope entropy及5种多尺度,应用于状态识别、故障诊断!
人工智能·算法·matlab·时序分析·故障诊断·信息熵·特征提取
清同趣科研4 小时前
R绘图|6种NMDS(非度量多维分析)绘图保姆级模板——NMDS从原理到绘图,看师兄这篇教程就够了
人工智能·算法
杜小暑4 小时前
冒泡排序与回调函数——qsort
c语言·算法·排序算法
徵6864 小时前
代码训练day27贪心算法p1
算法·贪心算法
purrrew5 小时前
【数据结构_5】链表(模拟实现以及leetcode上链表相关的题目)
数据结构·leetcode·链表
Nigori7_5 小时前
day32-动态规划__509. 斐波那契数__70. 爬楼梯__746. 使用最小花费爬楼梯
算法·动态规划