写出c语言代码:给一非空的单词列表,返回前 k 个出现次数最多的单词。 返回的答案应该按单词出现频率由高到低排序。如果不同的单词有相同出现频率,按字母顺序排序。 输入:第1行为k值,第2行单词列表,单词列表以end结尾,end不属于单词列表中的单词。 2 i love leetcode i love coding end 输出: i love
时间: 2024-02-06 21:12:02 浏览: 79
好的,下面是具体的 C 语言代码实现:
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_LEN 1000
// 定义哈希表结构体
typedef struct {
char* word;
int count;
} Node;
// 定义优先队列结构体
typedef struct {
Node** data;
int size;
int capacity;
} PriorityQueue;
// 初始化优先队列
void initPriorityQueue(PriorityQueue* pq, int capacity) {
pq->data = (Node**)malloc(sizeof(Node*) * capacity);
pq->size = 0;
pq->capacity = capacity;
}
// 向优先队列中插入一个元素
void insert(PriorityQueue* pq, Node* node) {
if (pq->size == pq->capacity) return;
pq->data[pq->size++] = node;
int i = pq->size - 1;
while (i > 0) {
int parent = (i - 1) / 2;
if (pq->data[i]->count > pq->data[parent]->count ||
(pq->data[i]->count == pq->data[parent]->count &&
strcmp(pq->data[i]->word, pq->data[parent]->word) < 0)) {
Node* tmp = pq->data[i];
pq->data[i] = pq->data[parent];
pq->data[parent] = tmp;
} else {
break;
}
i = parent;
}
}
// 从优先队列中取出一个元素
Node* pop(PriorityQueue* pq) {
if (pq->size == 0) return NULL;
Node* ret = pq->data[0];
pq->data[0] = pq->data[--pq->size];
int i = 0;
while (i * 2 + 1 < pq->size) {
int left = i * 2 + 1;
int right = i * 2 + 2;
int maxIdx = i;
if (pq->data[left]->count > pq->data[maxIdx]->count ||
(pq->data[left]->count == pq->data[maxIdx]->count &&
strcmp(pq->data[left]->word, pq->data[maxIdx]->word) < 0)) {
maxIdx = left;
}
if (right < pq->size &&
(pq->data[right]->count > pq->data[maxIdx]->count ||
(pq->data[right]->count == pq->data[maxIdx]->count &&
strcmp(pq->data[right]->word, pq->data[maxIdx]->word) < 0))) {
maxIdx = right;
}
if (maxIdx != i) {
Node* tmp = pq->data[i];
pq->data[i] = pq->data[maxIdx];
pq->data[maxIdx] = tmp;
} else {
break;
}
i = maxIdx;
}
return ret;
}
// 释放优先队列
void freePriorityQueue(PriorityQueue* pq) {
free(pq->data);
}
// 哈希函数
int hash(char* word) {
int hash = 0;
for (int i = 0; i < strlen(word); i++) {
hash = hash * 31 + word[i];
}
return hash;
}
// 初始化哈希表
void initHashTable(Node** hashTable, int size) {
for (int i = 0; i < size; i++) {
hashTable[i] = NULL;
}
}
// 在哈希表中查找单词
Node* find(Node** hashTable, int size, char* word) {
int h = hash(word) % size;
Node* cur = hashTable[h];
while (cur != NULL && strcmp(cur->word, word) != 0) {
cur = cur->next;
}
return cur;
}
// 向哈希表中插入一个单词
void insertToHashTable(Node** hashTable, int size, char* word) {
int h = hash(word) % size;
Node* cur = hashTable[h];
while (cur != NULL) {
if (strcmp(cur->word, word) == 0) {
cur->count++;
return;
}
cur = cur->next;
}
Node* node = (Node*)malloc(sizeof(Node));
node->word = (char*)malloc(sizeof(char) * (strlen(word) + 1));
strcpy(node->word, word);
node->count = 1;
node->next = hashTable[h];
hashTable[h] = node;
}
// 统计单词出现次数并放入优先队列中
void countWords(Node** hashTable, int size, PriorityQueue* pq) {
for (int i = 0; i < size; i++) {
Node* cur = hashTable[i];
while (cur != NULL) {
insert(pq, cur);
cur = cur->next;
}
}
}
int main() {
int k;
scanf("%d", &k);
char word[MAX_LEN];
Node* hashTable[100000] = {NULL};
while (scanf("%s", word) != EOF && strcmp(word, "end") != 0) {
insertToHashTable(hashTable, 100000, word);
}
PriorityQueue pq;
initPriorityQueue(&pq, 100000);
countWords(hashTable, 100000, &pq);
for (int i = 0; i < k; i++) {
Node* node = pop(&pq);
if (node != NULL) {
printf("%s\n", node->word);
}
}
freePriorityQueue(&pq);
for (int i = 0; i < 100000; i++) {
Node* cur = hashTable[i];
while (cur != NULL) {
Node* tmp = cur;
cur = cur->next;
free(tmp->word);
free(tmp);
}
}
return 0;
}
```
以上代码使用了哈希表和优先队列两个数据结构来实现题目需求,具体实现细节可以看注释。
阅读全文