[英]This TRIE algorithm code runs on CS50 IDE compiler but goes into an infinite loop in TDM-GCC on Windows
编写此代码是为了使用TRIE数据结构在字典中搜索单词。 这段代码可以在我的CS50 IDE编译器上同时使用make(Clang)和GCC完美运行,并且始终能给出正确的答案,但是当我在GCC编译器(TDM-GCC)上运行相同的代码时,它将陷入无限循环。 它开始使用大量RAM(直到我强行关闭它之前,才占用512 MB)。 在两种情况下,我运行的代码完全相同。 同样在两种情况下,代码都能完美编译。
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
struct trieblock123;
typedef struct trieblock123 trieblock;
typedef trieblock *node;
struct trieblock123
{
char alphabet;
char reply[5];
node pnt;
};
typedef struct
{
node first;
int count;
}head;
void load(FILE* dict, head* header);
void init(node pointer);
int main(void)
{
FILE* dict = fopen("large", "r");
head* header = malloc(sizeof(head));
(*header).count = 0;
(*header).first = NULL;
node curtrie = NULL;
node temptrie = NULL;
node temptrie1 = NULL;
char temp;
temp = fgetc(dict);
int counter = 0;
temptrie = (node)(malloc(26 * sizeof(trieblock)));
int i;
for(i = 0; i < 26; i++)
{
(temptrie[i]).alphabet = (char)(((int)('a')) + i);
(temptrie[i]).pnt = NULL;
}
if(counter == 0)
{
(*header).first = temptrie;
}
while(((int)(temp) <= (int)('z') && (int)(temp) >= (int)('a')) || temp == '\n')
{
if(((int)(temp) > (int)('z') || (int)(temp) < (int)('a')) && temp != '\n')
break;
curtrie = temptrie;
while(temp != '\n')
{
char temp1;
temp1 = fgetc(dict);
if((curtrie[(int)(temp) - (int)('a')]).pnt == NULL)
{
if(temp1 != '\n')
{
temptrie1 = (node)(malloc(26 * sizeof(trieblock)));
for(i = 0; i < 26; i++)
{
(temptrie1[i]).alphabet = (char)(((int)('a')) + i);
(temptrie1[i]).pnt = NULL;
}
(curtrie[(int)(temp) - (int)('a')]).pnt = temptrie1;
curtrie = temptrie1;
}
else
{
strcpy((curtrie[(int)(temp) - (int)('a')]).reply, "yes");
}
}
else if((curtrie[(int)(temp) - (int)('a')]).pnt != NULL)
{
curtrie = (curtrie[(int)(temp) - (int)('a')]).pnt;
}
fseek(dict, -1 * sizeof(char), SEEK_CUR);
temp = fgetc(dict);
}
if(temp == '\n')
{
temp = fgetc(dict);
}
counter++;
}
(*header).count = counter;
char tocheck[100];
scanf("%s", tocheck);
i = 0;
node start = NULL;
start = temptrie;
for(i = 0; i < strlen(tocheck); i++)
{
char cha = tocheck[i];
if(i != strlen(tocheck) - 1)
{
if((start[(int)(cha) - (int)('a')]).pnt == NULL)
{
printf("mis-spelled\n");
break;
}
else
{
start = (start[(int)(cha) - (int)('a')]).pnt;
}
}
else
{
if(strcmp(((start[(int)(cha) - (int)('a')]).reply), "yes") == 0)
{
printf("correctly spelled\n");
break;
}
else
{
printf("mis-spelled\n");
break;
}
}
}
return 0;
}
但是,这可能不是您期望的答案。
由于以下问题,您的代码难以调试和维护:
其他一些问题是:
这应该是等效的(除非我搞砸了):
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
typedef struct node_s node_t;
struct node_s {
char alphabet;
char present;
node_t *pnt;
};
typedef struct {
node_t *first;
int count;
} head_t;
#define NLETTERS 26
inline static int is_letter(char c) { return c <= 'z' && c >= 'a'; }
inline static node_t* new_trieblock() {
const int size = NLETTERS * sizeof(node_t);
node_t* block = malloc(size);
memset(block, 0, size);
for (int i = 0; i < NLETTERS; i++) {
block[i].alphabet = 'a' + i;
}
return block;
}
inline static int trie_has(node_t *n, char *str) {
node_t *trie = n;
int len = strlen(str);
for (int i = 0; i < len - 1; i++) {
trie = trie[str[i] - 'a'].pnt;
if (!trie) return 0;
}
return trie[str[len-1] - 'a'].present;
}
int main(void) {
FILE* dict = fopen("large", "r");
head_t *header = malloc(sizeof(head_t));
header->count = 0;
header->first = new_trieblock();
node_t *trie = header->first;
char c = fgetc(dict);
int nc;
while(is_letter(c) || c == '\n') {
nc = fgetc(dict);
if (nc == '\n' || nc == EOF) {
trie[c - 'a'].present = 1;
header->count++;
} else {
if (!trie[c - 'a'].pnt) {
trie = trie[c - 'a'].pnt = new_trieblock();
} else {
trie = trie[c - 'a'].pnt;
}
}
c = nc;
while (c == '\n') {
trie = header->first;
c = fgetc(dict);
}
}
char tocheck[100];
scanf("%s", tocheck);
if (trie_has(header->first, tocheck)) {
printf("correctly spelled\n");
} else {
printf("mis-spelled\n");
}
return 0;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.