给定两个数组,编写一个函数来计算它们的交集。
实施例: 给定nums1 = [1,2,2,1],nums2 = [2,2],返回[2]。
注意:
结果中的每个元素都必须是唯一的。
结果可以是任何顺序。
我首先使用两个循环来解决这个问题,并且弹出RunTime Error,因为复杂度为O(n ^ 2)。然后,我查找了许多解决方案,但没有一个是用C语言编写的。但是,我在C ++中找到了一个使用hashset的解决方案,这个解决方案是O(m + n)复杂度。
解决方案在这里:
public class Solution {
public int[] intersection(int[] nums1, int[] nums2) {
if(nums1.length==0||nums2.length==0)
return new int[0];
Set<Integer> result = new HashSet();
Set<Integer> set1 = new HashSet();
for(int i=0;i<nums1.length;i++){
set1.add(nums1[i]);
}
for(int i=0;i<nums2.length;i++){
if(set1.contains(nums2[i]))
result.add(nums2[i]);
}
int[] res = new int[result.size()];
int i=0;
Iterator iter = result.iterator();
while(iter.hasNext()){
res[i++]=(int)iter.next();
}
return res;
}
}
我想在C中使用哈希表,所以我自己定义一个哈希表结构并编写一个hashFind函数来查找该值是否在哈希表中。但是,RunTime Error仍然会弹出。我想问一下问题是否源于我的hashFind函数?但是,我认为既然我定义了足够大的哈希表并且来自leetcode的给定数据不是那么大,我的算法的复杂性也应该是O(m + n)。
这是我的代码:
/**
* Return an array of size *returnSize.
* Note: The returned array must be malloced, assume caller calls free().
*/
#define HASHSIZE 1007
static int hashf(int key) {
return key % HASHSIZE;
}
typedef struct listnode {
int val;
struct listnode *next;
} listnode;
typedef struct hashtable {
listnode **hash;
} hashtable;
static hashtable *hashCreat(void) {
hashtable *h;
int i;
if ((h = (hashtable *) malloc(sizeof(hashtable))) == NULL) return NULL;
if ((h->hash = (listnode **) malloc(sizeof(listnode *) * HASHSIZE)) == NULL) return NULL;
for (i = 0; i < HASHSIZE; i++)
h->hash[i] = NULL;
return h;
}
static void hashRelease(hashtable *h) {
listnode *current, *tmp;
int i;
for (i = 0; i < HASHSIZE; i++) {
current = h->hash[i];
while (current != NULL) {
tmp = current->next;
free(current);
current = tmp;
}
}
free(h->hash);
free(h);
}
static void hashInsert(hashtable *h, int key) {
int value;
listnode *node;
listnode *current;
if ((node = (listnode *) malloc(sizeof(listnode))) ==NULL) return NULL;
value = hashf(key);
current = h->hash[value];
while (current != NULL) {
if (current->val == key) return;
current = current->next;
}
node->next = h->hash[value];
h->hash[value] = node;
node->val = key;
}
static bool hashFind(hashtable *h, int key) {
int value;
listnode *current;
value = hashf(key);
current = h->hash[value];
while (current != NULL) {
if (current->val = key) return 1;
current = current->next;
}
return 0;
}
int* intersection(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize) {
if (nums1Size == 0 || nums2Size == 0) return NULL;
int *result;
int i, j;
int pos;
hashtable *h;
if ((result = (int *) malloc(sizeof(int) * *returnSize)) ==NULL) return NULL;
h = hashCreat();
pos = 0;
for (i = 0; i < nums1Size; i++)
hashInsert(h, nums1[i]);
for (j = 0; j < nums2Size; j++)
if (hashFind(h, nums2[j]))
result[pos++] = nums2[j];
hashRelease(h);
return result;
}
提前感谢您的回答或评论。
答案 0 :(得分:-1)
运行时错误表示您的代码在运行时没有正确执行和退出。它不是时间复杂度(TLE - 超出时间限制)或空间complxity(MLE - 超出内存限制)。运行时错误的原因有很多。其中,最常见的Leetcode问题是 - array out of bound
。可能是您正在尝试访问容器的某个索引,该索引已超出范围。
以下是您的修改和接受的解决方案:
/**
* Return an array of size *returnSize.
* Note: The returned array must be malloced, assume caller calls free().
*/
#define HASHSIZE 1007
static int hashf(int key) {
return key % HASHSIZE;
}
typedef struct listnode {
int val;
struct listnode *next;
} listnode;
typedef struct hashtable {
listnode **hash;
} hashtable;
static hashtable *hashCreat(void) {
hashtable *h;
int i;
if ((h = (hashtable *) malloc(sizeof(hashtable))) == NULL) return NULL;
if ((h->hash = (listnode **) malloc(sizeof(listnode *) * HASHSIZE)) == NULL) return NULL;
for (i = 0; i < HASHSIZE; i++)
h->hash[i] = NULL;
return h;
}
static void hashRelease(hashtable *h) {
listnode *current, *tmp;
int i;
for (i = 0; i < HASHSIZE; i++) {
current = h->hash[i];
while (current != NULL) {
tmp = current->next;
free(current);
current = tmp;
}
}
free(h->hash);
free(h);
}
static void hashInsert(hashtable *h, int key) {
int value;
listnode *node;
listnode *current;
// if ((node = (listnode *) malloc(sizeof(listnode))) ==NULL) return NULL;
// Correction: You can't return NULL from a void function
if ((node = (listnode *) malloc(sizeof(listnode))) ==NULL) return;
value = hashf(key);
current = h->hash[value];
while (current != NULL) {
if (current->val == key) return;
current = current->next;
}
node->next = h->hash[value];
h->hash[value] = node;
node->val = key;
}
static bool hashFind(hashtable *h, int key) {
int value;
listnode *current;
value = hashf(key);
current = h->hash[value];
while (current != NULL) {
// if (current->val = key) return 1;
// Correction: == instead of =
if (current->val == key) return 1;
current = current->next;
}
return 0;
}
int* intersection(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize) {
if (nums1Size == 0 || nums2Size == 0) return NULL;
int* result;
int i, j;
int pos;
hashtable *h;
// you need another hash to check if intersection array is including duplicate elements
hashtable *h2;
// if ((result = (int *) malloc(sizeof(int) * *returnSize)) ==NULL) return NULL;
// Correction: returnSize is the size of result array you have to return. Allocate minimum of two input array length as intersection array can't be bigger than smaller array
int minLength = (nums1Size < nums2Size ? nums1Size : nums2Size);
if ((result = (int *) malloc(sizeof(int) * (minLength + 1))) ==NULL) return NULL;
h = hashCreat();
h2 = hashCreat();
pos = 0;
for (i = 0; i < nums1Size; i++)
hashInsert(h, nums1[i]);
for (j = 0; j < nums2Size; j++)
if (hashFind(h, nums2[j])) {
// check if current element is already included or not
if(!hashFind(h2, nums2[j])) {
result[pos++] = nums2[j];
hashInsert(h2, nums2[j]);
}
}
hashRelease(h);
hashRelease(h2);
*returnSize = pos; // set the result array size which will be returned to caller as pass by reference
return result;
}
事实是 - 你在面试中没有机会实现自己的哈希表。因此,您应该学习并使用一些高级语言,如C ++,它们在标准库中具有这些数据结构。