2012-09-18 31 views
0

以下程序存储每个单词,然后用一些出现次数打印它们。
全球typedef声明:函数在结构数组中搜索 - 停止条件未知

typedef struct { 
    char * word; 
    int occ; 
} 
words; 
words *data=NULL; 

我有搜索功能的问题。我创建了一个函数返回int,看起来像这样:(max是结构数组的不断更新的大小,这就是为什么我把搜索功能达到EOF后)。

int search(char *word,int max) 
{ 
    int i; 
    for(i=0; i<max; i++) 
    { 
     if(!strcmp(data[i].word,word)) return i; 
    } 
    return -1; 
} 

但是我注意到我中号应该写具有原型搜索功能:

struct abc *find(char *word) 

所以我创建了下面的代码:

struct words *findword(char *word) 
{ 
    struct words *ptr; 

    for (ptr = data; ptr != NULL; ptr++) {  /* IS THE STOP CONDITION OK? */ 
     if (strcmp(word, ptr->word) == 0) 
      return ptr; 
    } 
    return NULL;   

} 

我在编译过程中收到许多错误:

reverse.c: In function ‘findword’:

reverse.c:73: warning: assignment from incompatible pointer type

reverse.c:73: error: increment of pointer to unknown structure

reverse.c:73: error: arithmetic on pointer to an incomplete type

reverse.c:74: error: dereferencing pointer to incomplete type

reverse.c: In function ‘main’:

reverse.c:171: error: ‘which’ undeclared (first use in this function)

reverse.c:171: error: (Each undeclared identifier is reported only once

reverse.c:171: error: for each function it appears in.)

make: * [reverse.o] Error 1


which是分配给我首先写的搜索功能返回的int变量。 与which该错误很容易固定,但我不知道如何替换(解决方案与我的基本搜索功能工作):

data[which].occ++;

如何解决此问题,以便它会与我的工作新的搜索方法?


编辑

main()补充说:

int main(int argc, char **argv) 
{ 
    char *word; 
    words *temp; 
    int c,i,num; 
    /*int which;*/ 
    FILE *infile; 

    if(argc!=2) {}  
    if((infile=fopen(argv[1],"r"))==NULL) {} 
    num=0; 
    while(1) 
    { 
     c=fgetc(infile); 
     if(c==EOF) break; 
     if(!isalpha(c)) continue; 
     else ungetc(c,infile); 
     word=getword(infile); 
     word=convert(word); 
     /*which=search(word,num);*/ 
     if(findword(word)) 
     { 
      if(!(temp=realloc(data,sizeof(words)*(num+1)))) 
      {} 
      else 
       data=temp; 
      data[num].word=strdup(word); 
      data[num].occ=1; 
      num++; 
     } 
     else 
      data[which].occ++; 

     free(word); 
    } 
    sort(num-1); 
    for(i=0;i<num;i++) 
    {} 
    free(data); 
    if(fclose(infile)) 
    {} 
    return 0; 
} 

我已经离开{}代码例如无关件。错误处理。


EDIT2 我所要求的上面的事,是固定的。但是,我现在遇到了seg故障。 我给一个链接到整个代码,我不想把它放在一个编辑的文章,因为它会造成一个大混乱。 Seg故障由第73行和第152行引起(strcmp无法正常工作)。希望完整的代码更容易理解。 FULL CODE

+0

为什么不只需将该'int max'参数移动到一个全局变量并使用第一个版本的代码?第二个版本将会崩溃,因为指针将会增加并增加超过'data []'数组的末尾。 –

+0

@AlexeyFrunze我不能使用第一个函数,因为它返回'int',我应该返回结构数组中的特定位置。 Ad.2 - 如何解决这个问题,以便指针在不断扩大的结构数组结尾处停止递增? –

+0

返回'&data [i]'而不是'i',那有什么问题?除了1)引入元素计数器(或指向最后一个元素的指针)并将当前检查的位置与该OR进行比较(我不建议这样做)之外,您不能修复该指针,2)将特殊指示符嵌入到数据[]的最后一个元素并检查它。 –

回答

2

的问题是与你的findword功能,让经过的所有线路

struct words *ptr; 

这不是你换货做什么。您在定义结构中使用的typedef允许您不必再编写struct。这就是为什么你会收到错误:reverse.c:73: error: increment of pointer to unknown structure。你想要的恰恰是:

words *ptr;  

接下来,循环:

for(ptr=data; //This is fine, you're assigning your local ptr to the global data. I assume that's something valid 

ptr != NULL; //That could OK too... we can loop while ptr is not NULL 
ptr++)  //This line makes no sense... 

您可能要查找如何for循环再工作,关键是,直到遇到一个条件你的东西递增。 ptr ++会移动到你指向的地方,所以你将不再指向你的结构。

我要看看你的main()功能,了解你想实现什么,而是基于你必须遵循的原型,我觉得最简单的解决办法是这样的:

void main() 
{ 
    // init your vars 
    bool more_words_to_add = true; 
    words *ptr = NULL; 
    int i; 

    // populate your array of words 
    while(more_words_to_add) { 
     for(i = 0; i<max; i++) { 
      if(ptr = findword("word")) //if we find the word 
      ptr->occ++; //increment the number of times we found it 
      else { 
      //I don't know what you want to do here, it's not clear what your goal is. 
      //Add the new word to your array of words and set occ to 1, 
      //then increment max because there's one more word in your array? 
      } 
     } 
     //get the next word to fine, or else set more_words_to_add = false to break 
    } 
} 

如果这的解决方案类型是你希望这样做,那么你可以调整你的findwords功能是非常简单的:

struct words *findword(char *word) 
{ 
    words *ptr = data; 
    if (strcmp(word, ptr->word) == 0) 
     return ptr; 
    return NULL; 
} 

编辑:为了您的新的错误,我怀疑,问题是你的备忘录RY配置,请参阅使用此结构的简单的例子:

words *findword(char *word) 
{ 
    words *ptr = data; 
    if(strcmp(word, ptr->word) == 0) 
     return ptr; 
    return NULL; 
} 

int main(){ 
    words *ptr; 

    data = realloc(data, sizeof(words)); 
    data->word = "hello";    //DO NOT SKIP THESE LINES 
    data->occ = 0;      //DO NOT SKIP THESE LINES 

    if(ptr = findword("hello")) { 
     ptr->occ++; 
     printf("I found %d %s's\n",ptr->occ, ptr->word); 
    } 
} 

[email protected]:~> ./a.out 
I found 1 hello's 

你可以看到这里,你需要的Alloc全球结构中的一些记忆,那么你可以将数据存储在它和传递指针给它。

编辑2:

main()代码做到这一点:

if((ptr = findword(word))) 
{ 
    //do stuff 
} 
else 
    ptr->occ++; 

这是行不通的,因为如果findword()失败则返回NULL,所以在如果检查PTR设为NULL,然后在别人你试图推迟NULL。如果(并且记住我真的不读你的逻辑,这是由你),你真的想增加ptr-> OCC如果找不到一个词,那么你要这个:

if(findword(word)) 
{ 
    ptr = findword(word); 
    //do stuff 
} 
else 
    ptr->occ++; //increments the current ptr's occ, no new ptr was assigned. 
+0

谢谢。我已经从编译阶段删除了所有错误(在您的帖子后面)。然而,现在我得到了分段错误,valgrind指出了两行导致错误:'main()'if(strcmp(word,ptr-> word)== 0)'和'if(findword(word))'这些有什么问题? –

+0

你的代码越来越难以考虑。你能完成这些新问题,你能清理它到当前版本吗?我怀疑问题是你的内存分配问题,请参阅我编辑的帖子,了解如何使用这个全局结构,看看是否有帮助。 – Mike

+0

我给一个链接到整个代码,我不想把它放在一个编辑的文章,因为它会造成一个大混乱。 Seg故障由线路73和152引起(strcmp不工作)。希望完整的代码更容易理解。 [链接](http://pastebin.com/t3t7Cr5D) –

1

在你的程序中没有这样的东西struct words;有一个未命名的struct类型,以及该类型的typedef words。一致使用struct wordswords

然后您就需要

result->occ++; 

其中result是您的新的搜索函数的返回值来代替

data[which].occ++; 

+0

正如你所看到的,我正在使用'words'。我想这是错误的名字,那么我应该改变什么来忽略那些编译错误? –

+0

@PeterKowalski不,你正在使用'struct words'。 – ecatmur

2
for (ptr = data; ptr != NULL; ptr++) {  
/* IS THE STOP CONDITION OK? */ 

不,你的指针只是不断增加。在该代码中唯一会使其成为NULL的是整数溢出。你可以看看它指向,并看看是否为空,如果你预设的数据区的0:

#define NUM_WORDS 100 
data = calloc(NUM_WORDS,sizeof(words)); 

或者

#define NUM_WORDS 100 
int bytes = NUM_WORDS * sizeof(words); 
data = malloc(bytes); 
memset(data,0,bytes); 

....

for (ptr = data; ptr->word != NULL; ptr++) { 

如果您不想将数据区预设为0,那么您必须将当前在数据区中保存的当前数量的结构传递给您的函数,以便知道要循环多少。