我有这四个文件,
test.c tinyll.h在/ home / user / code
并使用此说明进行编译以创建静态库 libtinyll.a并使用它。
; in lib
$ gcc -c tinyll.c
$ ar -cvq libtinyll.a *.o
; in code
$ gcc -o test test.c ../lib/libtinyll.a
直到这里一切都好。但我不知道为什么我会因为来自[CODE ERROR]但showElements的行而获得分段错误。目标不是从test.c传递代码到tinyll.c来处理链接的小列表。如何解决这个问题?
/////////////////////////////////// test.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "tinyll.h"
int main(int argc, char *argv[])
{
progname = argv[0];
char *file = "fwords";
int n;
PTLL lsone = NULL;
n = loadfileinTLL(file,&lsone);
// work. good.
showElements(lsone);
// [CODE ERROR]
// Why here dont work?
// segmentation fault, load the first word
// but in the second crash.
while (lsone != NULL) {
printf("%s",lsone->word);
lsone = lsone->next;
}
return 0;
}
/////////////////////////////////// tinyll.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "tinyll.h"
void addElement(PPTLL lst, char data[])
{
PTLL elemt;
elemt = (PTLL) malloc(sizeof(TLL));
if (elemt == NULL) {
fprintf(stderr, "%s: insufficient memory.\n", progname);
exit(1);
}
if (*lst == NULL)
{
strncpy(elemt->word, data, 45);
elemt->next = NULL;
*lst = elemt;
}
else {
// add in front of list
strncpy(elemt->word, data, 45);
elemt->next = *lst;
*lst = elemt;
}
}
void showElements(PTLL lst)
{
while (lst != NULL) {
printf("%s\n",lst->word);
lst = lst->next;
}
}
int loadfileinTLL(char *filepath, PPTLL plst)
{
FILE *f;
if ((f = fopen(filepath, "r")) == NULL) {
fprintf(stderr, "%s: error to load file %s.\n", progname, filepath);
exit(1);
}
char buf[45]; int n=0;
while (fgets(buf,sizeof(buf),f) != NULL) {
char *nl;
if ((nl = strchr(buf,'\n')) != NULL) {
*nl = '\0';
}
addElement(plst,buf);
n++;
}
fclose(f);
return n;
}
//////////////////////////////////// tinyll.h
#include <stdio.h>
#include <stdlib.h>
#ifndef _TINYLL_
#define _TINYLL_
struct list {
char word[45];
struct list *next;
};
// Tiny Linked List
typedef struct list TLL;
typedef struct list *PTLL;
typedef struct list **PPTLL;
char *progname;
#endif
答案 0 :(得分:0)
以下代码:
1) compiles cleanly
2) performs correctly, with out seg faulting.
3) checks and handles errors correctly
4) cleans up after itself, by freeing any allocated memory
5) removed leading underscores from names
as leading underscores has special meaning to the compiler
tinyll.h
#ifndef TINYLL_
#define TINYLL_
struct list
{
char word[45];
struct list *next;
};
// Tiny Linked List
typedef struct list TLL;
typedef struct list *PTLL;
typedef struct list **PPTLL;
extern char *progname;
void addElement(PPTLL lst, char data[]);
void showElements(PTLL lst);
int loadfileinTLL(char *filepath, PPTLL plst);
#endif // TINYLL_
tinyll.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "tinyll.h"
void addElement(PPTLL lst, char data[])
{
PTLL elemt;
elemt = (PTLL) malloc(sizeof(TLL));
if (elemt == NULL) {
fprintf(stderr, "%s: insufficient memory.\n", progname);
exit(1);
}
if (*lst == NULL)
{
strncpy(elemt->word, data, 45);
elemt->next = NULL;
*lst = elemt;
}
else {
// add in front of list
strncpy(elemt->word, data, 45);
elemt->next = *lst;
*lst = elemt;
}
}
void showElements(PTLL lst)
{
while (lst != NULL) {
printf("%s\n",lst->word);
lst = lst->next;
}
}
int loadfileinTLL(char *filepath, PPTLL plst)
{
int n=0;
FILE *f;
if ((f = fopen(filepath, "r")) == NULL)
{
fprintf(stderr, "%s: error to load file %s.\n", progname, filepath);
n = -1;
}
else
{
char buf[45];
while (fgets(buf,sizeof(buf),f) != NULL)
{
char *nl;
if ((nl = strchr(buf,'\n')) != NULL)
{
*nl = '\0';
}
addElement(plst,buf);
n++;
}
fclose(f);
} // endif
return n;
}
test.c的
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "tinyll.h"
char *progname;
int main(int argc, char *argv[])
{
if( 1 == argc )
{
progname = argv[0];
}
else
{
printf( "USAGE: %s\n", argv[0]);
exit( EXIT_FAILURE );
}
// implied else, right number (0) of arguments on command line
char *file = "fwords";
int n;
PTLL lsone = NULL;
PTLL lstwo = NULL;
n = loadfileinTLL(file,&lsone);
if( n > 0 )
{
// work. good.
showElements(lsone);
// [CODE ERROR]
// Why here dont work?
// segmentation fault, load the first word
// but in the second crash.
lstwo = lsone;
while (lstwo)
{
printf("%s",lstwo->word);
lstwo = lstwo->next;
}
} // endif
while( lsone )
{
lstwo = lsone->next;
free(lsone);
lsone = lstwo;
} // end while
return 0;
}
我将以下内容用于测试文件:
one
two
three
four
five
six
,输出结果为:
six
five
four
three
two
one
sixfivefourthreetwoone