4.16算法练习

两篇文章分别涉及LeetCode中的两个问题:求两个整数数组的交集,通过排序和双指针方法实现;以及判断一个字符串能否由另一个字符串的字符构成,通过字符频率数组进行检查。
摘要由CSDN通过智能技术生成

leetcode249:两个数组的交集

题目:

给定两个数组 nums1 和 nums2 ,返回 它们的 

交集

 。输出结果中的每个元素一定是 唯一 的。我们可以 不考虑输出结果的顺序 。

示例:

示例 1:

输入:nums1 = [1,2,2,1], nums2 = [2,2]
输出:[2]

示例 2:

输入:nums1 = [4,9,5], nums2 = [9,4,9,8,4]
输出:[9,4]
解释:[4,9] 也是可通过的

提示:

  • 1 <= nums1.length, nums2.length <= 1000
  • 0 <= nums1[i], nums2[i] <= 1000

解题思路:

排序 + 双指针
如果两个数组是有序的,则可以使用双指针的方法得到两个数组的交集。

首先对两个数组进行排序,然后使用两个指针遍历两个数组。可以预见的是加入答案的数组的元素一定是递增的

初始时,两个指针分别指向两个数组的头部。每次比较两个指针指向的两个数组中的数字,如果两个数字不相等,则将指向较小数字的指针右移一位,如果两个数字相等,将该数字添加到答案并更新 变量,同时将两个指针都右移一位。当至少有一个指针超出数组范围时,遍历结束。

代码实现:

int cmp(void* a, void* b) {
    return *(int*)a - *(int*)b;
}

int* intersection(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize) {
    qsort(nums1, nums1Size, sizeof(int), cmp);
    qsort(nums2, nums2Size, sizeof(int), cmp);
    *returnSize = 0;
    int index1 = 0, index2 = 0;
    int* intersection = malloc(sizeof(int) * (nums1Size + nums2Size));
    while (index1 < nums1Size && index2 < nums2Size) {
        int num1 = nums1[index1], num2 = nums2[index2];
        if (num1 == num2) {
            // 保证加入元素的唯一性
            if (!(*returnSize) || num1 != intersection[(*returnSize) - 1]) {
                intersection[(*returnSize)++] = num1;
            }
            index1++;
            index2++;
        } else if (num1 < num2) {
            index1++;
        } else {
            index2++;
        }
    }
    return intersection;
}

leetcode383:赎金信

题目:

给你两个字符串:ransomNote 和 magazine ,判断 ransomNote 能不能由 magazine 里面的字符构成。

如果可以,返回 true ;否则返回 false 。

magazine 中的每个字符只能在 ransomNote 中使用一次。

 示例:

示例 1:

输入:ransomNote = "a", magazine = "b"
输出:false

示例 2:

输入:ransomNote = "aa", magazine = "ab"
输出:false

示例 3:

输入:ransomNote = "aa", magazine = "aab"
输出:true

提示:

  • 1 <= ransomNote.length, magazine.length <= 105
  • ransomNote 和 magazine 由小写英文字母组成

解题思路:

要解决这个问题,我们可以使用一个类似的方法,即使用一个频率数组来统计 magazine 中每个字符的出现次数,然后遍历 ransomNote 来检查是否每个字符的出现次数都不超过在 magazine 中的对应次数。如果所有字符都满足这个条件,那么 ransomNote 可以由 magazine 里的字符构成,否则不可以。

这个函数首先遍历 magazine 字符串,统计每个字符的频率。然后,它遍历 ransomNote 字符串。对于 ransomNote 中的每个字符,它减少 magazine 中该字符的频率。如果发现任何字符的频率变为负数,这意味着 ransomNote 包含一个 magazine 中不存在的字符或者数量超过 magazine 中的对应字符,因此返回 false。如果遍历完 ransomNote 后没有遇到这种情况,就返回 true

代码实现:

bool canConstruct(char* ransomNote, char* magazine) {
    int frequency[256] = {0}; 
    for (int i = 0; magazine[i] != '\0'; i++) {
        frequency[magazine[i]]++;
    }
    for (int i = 0; ransomNote[i] != '\0'; i++) {
        if (--frequency[ransomNote[i]] < 0) {
            return false;
        }
    }
    return true;
}

  • 5
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值