C
cuiyouzhi0000
Dear friends,
I implemented a linked list in C, make, vim, gcc and gdb, could you
please verify me if I am wrong?
and how to improve them?
thanks very much!
------------Makefile-----------------------------
all: test
test: clean
gcc -g test.c linkedlist.c -o test.exe
clean:
-rm -rf test.exe
..PHONEY: clean all
---------------end-------------------------------
---------------constant.h---------------------
#ifndef _CONSTANT_
#define _CONSTANT_
#define JC_ERR_NO_MEMORY 10001
#define JC_ERR_NOT_FOUND 60001
#define JC_ERR_EMPTY_LIST 60002
#define JC_ERR_NOT_STACK_AND_QUEUE 60003
#define STACK 1
#define QUEUE 0
#endif
--------------------end----------------------
---------------errormap.h---------------------
#ifndef _ERRORMAP_
#define _ERRORMAP_
typedef struct {
int error;
const char *str;
} ErrorMap;
static
ErrorMap errorMap[] = {
{JC_ERR_NO_MEMORY, "no memory can be used"},
{JC_ERR_NOT_FOUND, "element not found in list"},
{JC_ERR_EMPTY_LIST, "empty list"},
{JC_ERR_NOT_STACK_AND_QUEUE, "pop not in stack and queue"},
};
#endif
----------------end-----------------------
---------------JC.h---------------------
#ifndef _JC_
#define _JC_
#include<stdio.h>
#include<stdlib.h>
#include "constant.h"
#include "errormap.h"
#endif
----------------end-------------------------
---------------linkedlist.h---------------------
#include "JC.h"
struct JCLinkedNode {
char *elem;
struct JCLinkedNode *next;
struct JCLinkedNode *prev;
};
struct JCLinkedList{
struct JCLinkedNode *first;
struct JCLinkedNode *last;
};
typedef struct JCLinkedNode JCLinkedNode;
typedef struct JCLinkedList JCLinkedList;
int JCLinkedList_Init(JCLinkedList **list);
int JCLinkedList_Free(JCLinkedList **list);
int JCLinkedList_Insert(JCLinkedList *list, const char* elem);
int JCLinkedList_Pop(JCLinkedList *list, int flag);
int JCLinkedList_Output(JCLinkedList *list);
------------------------end--------------------------------
--------------------linkedlist.c-------------------------------------
/* linked list*/
#include "linkedlist.h"
int
JCLinkedList_Init (JCLinkedList **list)
{
int status = 0;
*list = (JCLinkedList*) malloc(sizeof(JCLinkedList));
if ( NULL == *list ) {
status = JC_ERR_NO_MEMORY;
}
(*list)->first = NULL;
(*list)->last = NULL;
TERMINATE:
return status;
} /* End of JCLinkedList_Init */
/* Free the list*/
int
JCLinkedList_Free (JCLinkedList **list)
{
int status = 0;
while ( (*list)->first != NULL ) {
JCLinkedNode* oldp = (*list)->first;
(*list)->first = (*list)->first->next;
free (oldp->elem);
oldp->elem = NULL;
oldp->next = NULL;
free (oldp);
oldp = NULL;
}
(*list)->first = (*list)->last = NULL;
free (*list);
*list = NULL;
TERMINATE:
return status;
} /* End of JCLinkedList_Free */
int
JCLinkedList_Insert (JCLinkedList *list,
const char* elem)
{
int status = 0;
if ( list->first == NULL &&
list->last == NULL ) {
list->first =
(JCLinkedNode*) malloc (sizeof(JCLinkedNode));
list->last = list->first;
list->first->elem = (char*) malloc (strlen (elem) + 1);
if ( list->first->elem != NULL ) {
strcpy (list->first->elem, elem);
}
list->first->next = list->last->next = NULL;
list->first->prev = list->last->prev = NULL;
}
else {
list->last->next =
(JCLinkedNode*) malloc (sizeof(JCLinkedNode));
list->last->next->elem = (char*) malloc (strlen (elem) + 1);
if ( list->last->next->elem != NULL ) {
strcpy(list->last->next->elem, elem);
}
list->last->next->prev = list->last;
list->last->next->next = NULL;
list->last = list->last->next;
}
TERMINATE:
return status;
} /* END of JCLinkedList_Insert */
int
JCLinkedList_Output (JCLinkedList *list)
{
int count = 0;
struct JCLinkedNode *p;
if ( list->first != NULL &&
list->last != NULL ) {
p = list->first;
while ( p != list->last ) {
++count;
printf ("%s; ", p->elem);
p = p->next;
}
printf("%s.", p->elem);
++count;
printf ("\n");
printf("Have %d elements in this list\n\n", count);
}
return 0;
} /* End of JCLinkedList_Output */
// Pop is a method used in both stack and queue with flag
int
JCLinkedList_Pop (JCLinkedList *list, int flag)
{
int status = 0;
JCLinkedNode *p;
if ( flag == STACK) {
if ( list->first != NULL) {
p = list->first;
list->first = list->first->next;
free(p->elem);
p->elem = NULL;
}
else {
status = JC_ERR_EMPTY_LIST;
}
}
else if ( flag == QUEUE ) {
if ( list->last != NULL) {
p = list->last;
list->last = list->last->prev;
free(p->elem);
p->elem = NULL;
}
else {
status = JC_ERR_EMPTY_LIST;
}
}
else {
status = JC_ERR_NOT_STACK_AND_QUEUE;
}
TERMINATE:
return status;
} /* End of JCLinkedList_Pop */
-----------------end----------------------------------------
-----------------------test.c--------------------------------
#include "linkedlist.h"
int main(void)
{
int i;
int status = 0;
struct JCLinkedList* mylist = NULL;
status = JCLinkedList_Init (&mylist);
if ( status ) goto TERMINATE;
// insert 10 elements
for (i = 0; i < 10; ++i) {
status = JCLinkedList_Insert (mylist, "a");
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// insert 10 elements too
for (i = 0; i < 10; ++i) {
status = JCLinkedList_Insert (mylist, "b");
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// pop like stack
for (i = 0; i < 5; ++i) {
status = JCLinkedList_Pop (mylist, STACK);
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// pop like queue
for (i = 0; i < 5; ++i) {
status = JCLinkedList_Pop (mylist, QUEUE);
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
status = JCLinkedList_Free (&mylist);
if ( status ) goto TERMINATE;
if ( NULL == mylist ) printf ("free list successfully!\n");
TERMINATE:
if ( status ) {
int nErrors = sizeof (errorMap) / sizeof (ErrorMap);
for (i = 0; i < nErrors; ++i) {
if ( errorMap.error == status ) {
printf ("JC Error: %s\n", errorMap.str);
}
}
JCLinkedList_Free (&mylist);
}
return 0;
}
--------------end-----------------------------------
--------------------------------------------------------------------
output:
a; a; a; a; a; a; a; a; a; a.
Have 10 elements in this list
a; a; a; a; a; a; a; a; a; a; b; b; b; b; b; b; b; b; b; b.
Have 20 elements in this list
a; a; a; a; a; b; b; b; b; b; b; b; b; b; b.
Have 15 elements in this list
a; a; a; a; a; b; b; b; b; b.
Have 10 elements in this list
free list successfully!
I implemented a linked list in C, make, vim, gcc and gdb, could you
please verify me if I am wrong?
and how to improve them?
thanks very much!
------------Makefile-----------------------------
all: test
test: clean
gcc -g test.c linkedlist.c -o test.exe
clean:
-rm -rf test.exe
..PHONEY: clean all
---------------end-------------------------------
---------------constant.h---------------------
#ifndef _CONSTANT_
#define _CONSTANT_
#define JC_ERR_NO_MEMORY 10001
#define JC_ERR_NOT_FOUND 60001
#define JC_ERR_EMPTY_LIST 60002
#define JC_ERR_NOT_STACK_AND_QUEUE 60003
#define STACK 1
#define QUEUE 0
#endif
--------------------end----------------------
---------------errormap.h---------------------
#ifndef _ERRORMAP_
#define _ERRORMAP_
typedef struct {
int error;
const char *str;
} ErrorMap;
static
ErrorMap errorMap[] = {
{JC_ERR_NO_MEMORY, "no memory can be used"},
{JC_ERR_NOT_FOUND, "element not found in list"},
{JC_ERR_EMPTY_LIST, "empty list"},
{JC_ERR_NOT_STACK_AND_QUEUE, "pop not in stack and queue"},
};
#endif
----------------end-----------------------
---------------JC.h---------------------
#ifndef _JC_
#define _JC_
#include<stdio.h>
#include<stdlib.h>
#include "constant.h"
#include "errormap.h"
#endif
----------------end-------------------------
---------------linkedlist.h---------------------
#include "JC.h"
struct JCLinkedNode {
char *elem;
struct JCLinkedNode *next;
struct JCLinkedNode *prev;
};
struct JCLinkedList{
struct JCLinkedNode *first;
struct JCLinkedNode *last;
};
typedef struct JCLinkedNode JCLinkedNode;
typedef struct JCLinkedList JCLinkedList;
int JCLinkedList_Init(JCLinkedList **list);
int JCLinkedList_Free(JCLinkedList **list);
int JCLinkedList_Insert(JCLinkedList *list, const char* elem);
int JCLinkedList_Pop(JCLinkedList *list, int flag);
int JCLinkedList_Output(JCLinkedList *list);
------------------------end--------------------------------
--------------------linkedlist.c-------------------------------------
/* linked list*/
#include "linkedlist.h"
int
JCLinkedList_Init (JCLinkedList **list)
{
int status = 0;
*list = (JCLinkedList*) malloc(sizeof(JCLinkedList));
if ( NULL == *list ) {
status = JC_ERR_NO_MEMORY;
}
(*list)->first = NULL;
(*list)->last = NULL;
TERMINATE:
return status;
} /* End of JCLinkedList_Init */
/* Free the list*/
int
JCLinkedList_Free (JCLinkedList **list)
{
int status = 0;
while ( (*list)->first != NULL ) {
JCLinkedNode* oldp = (*list)->first;
(*list)->first = (*list)->first->next;
free (oldp->elem);
oldp->elem = NULL;
oldp->next = NULL;
free (oldp);
oldp = NULL;
}
(*list)->first = (*list)->last = NULL;
free (*list);
*list = NULL;
TERMINATE:
return status;
} /* End of JCLinkedList_Free */
int
JCLinkedList_Insert (JCLinkedList *list,
const char* elem)
{
int status = 0;
if ( list->first == NULL &&
list->last == NULL ) {
list->first =
(JCLinkedNode*) malloc (sizeof(JCLinkedNode));
list->last = list->first;
list->first->elem = (char*) malloc (strlen (elem) + 1);
if ( list->first->elem != NULL ) {
strcpy (list->first->elem, elem);
}
list->first->next = list->last->next = NULL;
list->first->prev = list->last->prev = NULL;
}
else {
list->last->next =
(JCLinkedNode*) malloc (sizeof(JCLinkedNode));
list->last->next->elem = (char*) malloc (strlen (elem) + 1);
if ( list->last->next->elem != NULL ) {
strcpy(list->last->next->elem, elem);
}
list->last->next->prev = list->last;
list->last->next->next = NULL;
list->last = list->last->next;
}
TERMINATE:
return status;
} /* END of JCLinkedList_Insert */
int
JCLinkedList_Output (JCLinkedList *list)
{
int count = 0;
struct JCLinkedNode *p;
if ( list->first != NULL &&
list->last != NULL ) {
p = list->first;
while ( p != list->last ) {
++count;
printf ("%s; ", p->elem);
p = p->next;
}
printf("%s.", p->elem);
++count;
printf ("\n");
printf("Have %d elements in this list\n\n", count);
}
return 0;
} /* End of JCLinkedList_Output */
// Pop is a method used in both stack and queue with flag
int
JCLinkedList_Pop (JCLinkedList *list, int flag)
{
int status = 0;
JCLinkedNode *p;
if ( flag == STACK) {
if ( list->first != NULL) {
p = list->first;
list->first = list->first->next;
free(p->elem);
p->elem = NULL;
}
else {
status = JC_ERR_EMPTY_LIST;
}
}
else if ( flag == QUEUE ) {
if ( list->last != NULL) {
p = list->last;
list->last = list->last->prev;
free(p->elem);
p->elem = NULL;
}
else {
status = JC_ERR_EMPTY_LIST;
}
}
else {
status = JC_ERR_NOT_STACK_AND_QUEUE;
}
TERMINATE:
return status;
} /* End of JCLinkedList_Pop */
-----------------end----------------------------------------
-----------------------test.c--------------------------------
#include "linkedlist.h"
int main(void)
{
int i;
int status = 0;
struct JCLinkedList* mylist = NULL;
status = JCLinkedList_Init (&mylist);
if ( status ) goto TERMINATE;
// insert 10 elements
for (i = 0; i < 10; ++i) {
status = JCLinkedList_Insert (mylist, "a");
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// insert 10 elements too
for (i = 0; i < 10; ++i) {
status = JCLinkedList_Insert (mylist, "b");
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// pop like stack
for (i = 0; i < 5; ++i) {
status = JCLinkedList_Pop (mylist, STACK);
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
// pop like queue
for (i = 0; i < 5; ++i) {
status = JCLinkedList_Pop (mylist, QUEUE);
if ( status ) goto TERMINATE;
}
status = JCLinkedList_Output (mylist);
if ( status ) goto TERMINATE;
status = JCLinkedList_Free (&mylist);
if ( status ) goto TERMINATE;
if ( NULL == mylist ) printf ("free list successfully!\n");
TERMINATE:
if ( status ) {
int nErrors = sizeof (errorMap) / sizeof (ErrorMap);
for (i = 0; i < nErrors; ++i) {
if ( errorMap.error == status ) {
printf ("JC Error: %s\n", errorMap.str);
}
}
JCLinkedList_Free (&mylist);
}
return 0;
}
--------------end-----------------------------------
--------------------------------------------------------------------
output:
a; a; a; a; a; a; a; a; a; a.
Have 10 elements in this list
a; a; a; a; a; a; a; a; a; a; b; b; b; b; b; b; b; b; b; b.
Have 20 elements in this list
a; a; a; a; a; b; b; b; b; b; b; b; b; b; b.
Have 15 elements in this list
a; a; a; a; a; b; b; b; b; b.
Have 10 elements in this list
free list successfully!