ac自动机匹配new与malloc分配结点空间问题
程序代码:
#include <stdio.h> #include <string.h> #include <memory.h> #include <malloc.h> const int kind = 26;//表示26个字母的编号 struct Mynode { struct Mynode *next[kind];//表示每个节点都可以有26个字母作为其孩子 struct Mynode *fail; int flag;//标志以该节点回溯的单词可以匹配 Mynode() { fail = NULL; flag = 0; memset(next, NULL, sizeof(next));//所有的孩子都初始化为NULL } };// Mynode *lpMyseque[500001];//指针队列用来构造失败指针的 char szMsg[256];//单词 char str[100000];//文本 int start = -1;//队列的头指针 int last = -1;//队列的末尾指针 void CreateTree(Mynode* root);//创建字典树 void InsertWord(char* keyword, Mynode* root);//插入单词 void CreateAc(Mynode* root);//创建自动机 int FindMacthWord(Mynode* root);//返回匹配的单词数目 void CreateTree(Mynode* root) { int n; scanf("%d", &n);//输入单词数 getchar(); while(n) { gets(szMsg); InsertWord(szMsg, root); n--; } return; } void InsertWord(char* keyword, Mynode* root) { Mynode* p = root; int i = 0; int index; while(keyword[i]) { index = keyword[i] - 'a';//转化为0到25数字 if (p->next[index] == NULL) { p->next[index] = new Mynode();//为单词中的每一个字符分配空间 //p->next[index] = (Mynode*)malloc(sizeof(Mynode)); } p = p->next[index];//p指向该新建立的节点 i++; } p->flag++;//该单词的标志 return; } //构造失败指针 void CreateAc(Mynode* root) { int i; root->fail = NULL;//根节点的失败指针指向空 lpMyseque[++start] = root;//进队列 while(start != last) { Mynode* temp = lpMyseque[++last];//出队列 Mynode* p = NULL; for (i=0; i<26; i++) { if (temp->next[i] != NULL) { if (temp == root) { temp->next[i]->fail = root;//root后的第一个节点失败指针指向root } //不是第一个节点的 else { p = temp->fail; while(p != NULL) { if (p->next[i] != NULL) { temp->next[i]->fail = p->next[i]; break; } //如果在p->next中没有找到与temp->next相同的字符 p = p->fail;//就把p指向失败节点 } //如果p中指向的所有的失败节点都没有与之相同的孩子 if (NULL == p) { temp->next[i]->fail = root;//temp孩子的失败指针就指向root } } lpMyseque[++start] = temp->next[i];//进入队列 } } } return; } //寻找匹配的单词的个数 int FindMacthWord(Mynode* root) { int i = 0; int count = 0;//计算匹配的单词的个数 int index;//字符的标号 int len = strlen(str);//文本的长度 Mynode* p = root; while(str[i]) { index = str[i] - 'a'; while(p->next[index] == NULL && p != root) p = p->fail; p = p->next[index]; p = (p == NULL) ? root : p; Mynode* temp = p; while(temp != root && temp->flag != -1) { count += temp->flag;//如果是单词的末尾字符flag为1否则就是0 temp->flag = -1; temp = temp->fail; } i++; } return count; } int main() { //Mynode* root = (Mynode*)malloc(sizeof(Mynode));; Mynode* root = new Mynode(); CreateTree(root); gets(str); CreateAc(root); printf("%d\n",FindMacthWord(root)); return 0; }我用了两种方法来开辟结点的空间。
第一种方法为new
Mynode* root = new Mynode();
第二种为malloc
Mynode* root = (Mynode*)malloc(sizeof(Mynode));
new方法运行没有错,malloc运行方法程序崩溃。出错在InsertWord函数中
if (p->next[index] == NULL)
或者
p->flag++;
这两个地方。
有兴趣的帮忙看看!!谢谢
[ 本帖最后由 ycc892009 于 2010-11-18 23:24 编辑 ]