leetcode347.前k个高频元素

leetcode347.前k个高频元素

给你一个整数数组 nums 和一个整数 k ,请你返回其中出现频率前 k 高的元素。你可以按 任意顺序 返回答案。
示例 1:
输入: nums = [1,1,1,2,2,3], k = 2
输出: [1,2]

示例 2:
输入: nums = [1], k = 1
输出: [1]

优先队列法

struct hash_table {
    int key;
    int val;
    UT_hash_handle hh;
};//表示一个哈希表条目,包含key和val字段。
//定义一个指向hash_table结构的指针。
typedef struct hash_table* hash_ptr;

struct pair {
    int first;
    int second;
};//表示一对整数。

struct pair* heap;//用作堆的整数对数组。
int heapSize;//堆的大小的变量。

void swap(struct pair* a, struct pair* b) {
    struct pair t = *a;
    *a = *b, *b = t;
}

bool cmp(struct pair* a, struct pair* b) {
    return a->second < b->second;
}

struct pair top() {//返回堆顶元素。
    return heap[1];
}

int push(hash_ptr x) {//将新元素推入堆并维护堆属性。
    heap[++heapSize].first = x->key;
    heap[heapSize].second = x->val;
    int p = heapSize, s;
    while (p > 1) {
        s = p >> 1;
        if (cmp(&heap[s], &heap[p])) return 0;
        swap(&heap[p], &heap[s]);
        p = s;
    }
    return 1;
}

int pop() {
    heap[1] = heap[heapSize--];
    int p = 1, s;
    while ((p << 1) <= heapSize) {
        s = p << 1;
        if (s < heapSize && cmp(&heap[s + 1], &heap[s])) s++;
        if (cmp(&heap[p], &heap[s])) return 0;
        swap(&heap[p], &heap[s]);
        p = s;
    }
    return 1;
}

int* topKFrequent(int* nums, int numsSize, int k, int* returnSize) {
    hash_ptr head = NULL;
    hash_ptr p = NULL, tmp = NULL;

    for (int i = 0; i < numsSize; i++) {//遍历数组,计算每个元素出现频率,并将其存储在哈希表中
        HASH_FIND_INT(head, &nums[i], p);
        if (p == NULL) {
            p = malloc(sizeof(struct hash_table));
            p->key = nums[i];
            p->val = 1;
            HASH_ADD_INT(head, key, p);
        } else {
            p->val++;
        }
    }
    //堆初始化
    heap = malloc(sizeof(struct pair) * (k + 1));
    heapSize = 0;

    /*如果堆的元素个数等于 k,则检查堆顶与当前出现次数的大小。
    如果堆顶更大(小根堆堆顶元素为最小值),说明至少有 k个数字的出现次数比当前值大,故舍弃当前值;
    否则,就弹出堆顶,并将当前值插入堆中。*/
    /*HASH_ITER(hh, head, p, tmp) {//查找前k个频繁元素
        if (heapSize == k) {//堆已满(大小 == k)
            struct pair tmp = top();
            if (tmp.second < p->val) {//将堆顶元素与当前元素进行比较
                pop();//当前元素的频率更高,它会替换堆顶元素。
                push(p);//将p推入堆中
            }
        } else {
            push(p);//堆大小不等于k直接入栈
        }
    }
    /*它从堆中检索顶部元素并将其存储在临时变量 tmp 中。
    它从堆中弹出顶部元素。
    它将 tmp 的第一个值赋给数组 ret 的第 i 个元素。*/
    /**returnSize = k;
    int* ret = malloc(sizeof(int) * k);
    for (int i = k-1; i >=0; i--) {//逆序输出堆元素
        struct pair tmp = top();
        pop();
        ret[i] = tmp.first;
    }
    return ret;
}

暴力法

#include <stdio.h>
#include <stdlib.h>

// 结构体用于存储元素和其出现的频率
typedef struct {
    int num;
    int freq;
} Element;

// 比较函数,用于qsort排序
int compare(const void *a, const void *b) {
    return ((Element *)b)->freq - ((Element *)a)->freq;
}

int* topKFrequent(int* nums, int numsSize, int k, int* returnSize) {
    // 统计每个元素的频率
    Element *elements = (Element *)malloc(numsSize * sizeof(Element));
    int count = 0;
    for (int i = 0; i < numsSize; i++) {
        int j;
        for (j = 0; j < count; j++) {
            if (elements[j].num == nums[i]) {
                elements[j].freq++;
                break;
            }
        }
        if (j == count) {
            elements[count].num = nums[i];
            elements[count].freq = 1;
            count++;
        }
    }

    // 对元素按频率进行排序
    qsort(elements, count, sizeof(Element), compare);

    // 返回前k个高频元素
    int *result = (int *)malloc(k * sizeof(int));
    *returnSize = k;
    for (int i = 0; i < k; i++) {
        result[i] = elements[i].num;
    }

    free(elements);
    return result;
}
  • 7
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

我不会起名字呀

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值