我的代码给出了glibc错误。有人请指出我的错误。 此代码用于标记单词。如何使用GDB或任何其他有用的工具解决这些问题。代码如下:
#include <stdio.h>
#include <stdlib.h>
#include <glib.h>
#include <string.h>
struct token
{
char *token;
int length;
};
void freeing(gpointer item)
{
free(((struct token*)item)->token);
}
int main(int argc, char* argv[])
{
int start1 = 0, start2 = 0, i =0;
struct token *tk = NULL;
char line[256], *temp = NULL;
FILE *fp1 = NULL;
FILE *fp2 = NULL;
GSList *list = NULL, *iterator = NULL;
fp1 = fopen(argv[1], "r");
fp2 = fopen(argv[2], "w+");
if (NULL == fp1)
{
fprintf(stderr,"cant open %s",argv[1]);
return 1;
}
if (NULL == fp2)
{
fprintf(stderr,"cant open %s",argv[2]);
return 1;
}
while (1)
{
if (NULL == fgets(line, 255, fp1))
break;
tk = (struct token *)malloc(sizeof(struct token));
start1 = -1; start2 = -1;
for(temp = line,i = 0; temp[i] != '\n'; i++)
{
if ((temp[i] == ',') || (temp[i] == ' ') || (temp[i] == ';') || (temp[i] == '.'))
start2 = i;
if (start1 == start2)
continue;
tk->token = strndup(line + (start1+1), start2 - (start1+1));
tk->length = strlen(tk->token);
list = g_slist_append(list, tk);
start1 = start2;
}
tk->token = strndup(line + (start1+1), strlen(line));
tk->length = strlen(tk->token);
printf("\ntk->length : %d\n",tk->length);
list = g_slist_append(list, tk );
}
for (iterator = list; iterator; iterator = iterator->next)
{
printf("%s -> ",((struct token *)(iterator->data))->token);
printf("%d\n",((struct token*)iterator->data)->length);
}
g_slist_foreach(list, (GFunc)freeing, NULL);
fclose(fp1);
fclose(fp2);
return 0;
}
答案 0 :(得分:1)
以下代码修复了主要问题,但没有修复循环中的逻辑错误:
for(int i=0, temp = line; temp[i] != '\n'; i++)
{
...
}
tk->token = strndup(line + (start1+1), strlen(line));
tk->length = strlen(tk->token);
printf("\ntk->length : %d\n",tk->length);
list = g_slist_append(list, tk );
以下针对发布代码中的大多数问题的建议修正更正:
添加了对g_slist_free(list);
的最终调用,因此struct token
的所有实例都返回到堆中。
#define _GNU_SOURCE
#include <stdio.h>
#include <stdlib.h>
#include <glib.h>
#include <string.h>
#define MAX_LINE_LEN (256)
struct token
{
char *token;
int length;
};
void freeing(gpointer item)
{
free(((struct token*)item)->token);
}
int main(int argc, char* argv[])
{
if( 3 != argc )
{ // then incorrect number of command line arguments
fprintf( stderr, "USAGE: %s <inputfile> <outputfile>\n", argv[0]);
exit( EXIT_FAILURE );
}
// implied else, correct number of command line arguments
FILE *fp1 = NULL;
FILE *fp2 = NULL;
if( NULL == (fp1 = fopen(argv[1], "r") ) )
{ // then fopen failed
fprintf( stderr, "fopen for %s for read failed\n", argv[1]);
exit( EXIT_FAILURE );
}
// implied else, fopen successful
if( NULL == (fp2 = fopen(argv[2], "w+") ) )
{ // then fopen failed
fprintf( stderr, "fopen for %s for write failed\n", argv[2]);
fclose( fp1 ); // cleanup
exit( EXIT_FAILURE );
}
// implied else, fopen successful
GSList *list = NULL;
GSList *iterator = NULL;
char line[ MAX_LINE_LEN ];
struct token *tk = NULL;
char *temp = NULL;
while ( fgets(line, sizeof(line), fp1) )
{
if( NULL == (tk = malloc(sizeof(struct token)) ) )
{ // then malloc failed
perror( "malloc for struct token failed");
fclose( fp1 );
fclose( fp2 );
exit( EXIT_FAILURE );
}
// implied else, malloc successful
size_t start1 = 0;
size_t start2 = 0;
temp = line;
for(size_t i=0; temp[i] != '\n'; i++)
{
if ((temp[i] == ',') || (temp[i] == ' ') || (temp[i] == ';') || (temp[i] == '.'))
start2 = i;
if (start1 == start2)
continue;
tk->token = strndup(line + (start1+1), start2 - (start1+1));
tk->length = (int)strlen(tk->token);
list = g_slist_append(list, tk);
start1 = start2;
} // end for
tk->token = strndup(line + (start1+1), strlen(line));
tk->length = (int)strlen(tk->token);
printf("\ntk->length : %d\n",tk->length);
list = g_slist_append(list, tk );
} // end while
for (iterator = list; iterator; iterator = iterator->next)
{
printf("%s -> ",((struct token *)(iterator->data))->token);
printf("%d\n",((struct token*)iterator->data)->length);
}
g_slist_foreach(list, (GFunc)freeing, NULL);
g_slist_free(list);
fclose(fp1);
fclose(fp2);
return 0;
}