Every day a leetcode
题目来源:350. 两个数组的交集 II
解法1:排序 + 双指针
先将两个数组排序。
然后使用两个指针遍历两个数组。
初始时,两个指针分别指向两个数组的头部。每次比较两个指针指向的两个数组中的数字:
- 如果两个数字不相等,则将指向较小数字的指针右移一位;
- 如果两个数字相等,将该数字添加到答案,并将两个指针都右移一位。
当至少有一个指针超出数组范围时,遍历结束。
代码:
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
int min(int a,int b)
{
return a>b?b:a;
}
int cmpfunc (const void * a, const void * b)
{
return ( *(int*)a - *(int*)b );
}
int* intersect(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize){
*returnSize=0;
int ansSize=min(nums1Size,nums2Size);
int *ans;
ans=(int*)malloc(ansSize*sizeof(int));
int p=0;
int q=0;
qsort(nums1,nums1Size,sizeof(int),cmpfunc);
qsort(nums2,nums2Size,sizeof(int),cmpfunc);
while(p<nums1Size && q<nums2Size)
{
if(nums1[p]<nums2[q]) p++;
else if(nums1[p]>nums2[q]) q++;
else
{
ans[(*returnSize)++]=nums1[p];
p++;
q++;
}
}
return ans;
}
结果:
解法2:hash
首先遍历第一个数组,并在哈希表中记录第一个数组中的每个数字以及对应出现的次数,然后遍历第二个数组,对于第二个数组中的每个数字,如果在哈希表中存在这个数字,则将该数字添加到答案,并减少哈希表中该数字出现的次数。
因为可以不考虑输出结果的顺序,所以不用对第二个数组排序。
代码:
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
#define MAX_HASH_LENGTH 1001
int min(int a,int b)
{
return a>b?b:a;
}
int* intersect(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize){
*returnSize=0;
int hash[MAX_HASH_LENGTH];
memset(hash,0,sizeof(hash));
int ansSize=min(nums1Size,nums2Size);
int *ans;
ans=(int*)malloc(ansSize*sizeof(int));
for(int i=0;i<nums1Size;i++) hash[nums1[i]]++;
for(int i=0;i<nums2Size;i++)
{
if(hash[nums2[i]]>0)
{
ans[(*returnSize)++]=nums2[i];
hash[nums2[i]]--;
}
}
return ans;
}
结果: