1 #ifndef LIST_H 2 #define LIST_H 3 4 typedef unsigned int Item; 5 typedef unsigned char byte; 6 struct node 7 { 8 Item item; // 卫星数据 9 struct node * next; 10 }; 11 typedef struct node * List; 12 13 void ListAddItem(List *plist, const Item item); 14 struct node * ListSearchItem(const List list, const Item item); 15 void ListDelItem(List *plist, const Item item); 16 void ListDel(List *plist); 17 void ListInvert(List *plist); 18 bool ListIsLoop(const List list); 19 struct node * ListConcatenate(List list1, List list2); 20 #endif
1 #include "stdafx.h" 2 #include "list.h" 3 #include <assert.h> 4 #include <malloc.h> 5 6 static inline void CopyItem(Item item, struct node* pnode) 7 { 8 pnode->item = item; 9 } 10 11 static inline int ItemCmp(Item item1, Item item2) 12 { 13 return item1 > item2 ? 1 : (item1 == item2 ? 0 : -1); 14 } 15 16 17 /********************************************** 18 向链表中插入节点 19 当链表为空时,需要改变链表头所指向的内容,因此入参用链表头指针 20 **********************************************/ 21 void ListAddItem(List *plist, const Item item) 22 { 23 assert(NULL != plist); 24 25 struct node *pnew; 26 pnew = (struct node *)malloc(sizeof(struct node)); 27 assert(NULL != pnew); 28 29 CopyItem(item,pnew); 30 31 // 从小到大排列 32 struct node *pscan = *plist; 33 struct node *pinsert = NULL; 34 while (NULL != pscan) 35 { 36 // 若是只需要插入到链表尾,可以去掉if-else条件,将循环体改为 37 // pinsert = pscan; pscan = pscan->next; 38 if (ItemCmp(pscan->item, item) < 0) 39 { 40 pinsert = pscan; 41 pscan = pscan->next; 42 } 43 else 44 { 45 break; 46 } 47 } 48 49 // 无比item小的节点或是空链表,链表头插入 50 if (NULL == pinsert) 51 { 52 pnew->next = pscan; 53 *plist = pnew; 54 } 55 else // 链表中间或者链表尾部 56 { 57 pnew->next = pscan; 58 pinsert->next = pnew; 59 } 60 } 61 62 /********************************************** 63 若相应的item存在,则返回第一个item的前驱(头节点的 64 前驱为NULL) 65 否则返回NULL 66 **********************************************/ 67 struct node * ListSearchItem(const List list, const Item item) 68 { 69 struct node * pscan = list; 70 struct node * pprev = NULL; 71 72 while (NULL != pscan) 73 { 74 if (ItemCmp(pscan->item, item) == 0) 75 { 76 return pprev; 77 } 78 else 79 { 80 pprev = pscan; 81 pscan = pscan->next; 82 } 83 } 84 85 return NULL; 86 } 87 88 89 /********************************************** 90 // 删除元素 91 // 返回值:0,删除失败(不存在该item),1:删除成功 92 **********************************************/ 93 void ListDelItem(List *plist, const Item item) 94 { 95 assert(NULL != plist); 96 97 struct node *ptemp = *plist; 98 if (NULL == ptemp) // 空链表 99 return; 100 101 struct node *pdel = ListSearchItem(*plist, item); 102 if (NULL == pdel) 103 { 104 if (ItemCmp((*plist)->item, item) == 0) 105 { 106 pdel = *plist; 107 *plist = pdel->next; 108 free(pdel); 109 } 110 } 111 else 112 { 113 ptemp = pdel->next; // item所在节点 114 pdel->next = pdel->next->next; 115 free(ptemp); 116 } 117 } 118 119 120 /********************************************** 121 // 删除链表 122 **********************************************/ 123 void ListDel(List *plist) 124 { 125 assert(NULL != plist); 126 127 struct node *pscan; 128 struct node *pdel; 129 130 pscan = *plist; 131 132 while (NULL != pscan) 133 { 134 pdel = pscan; 135 pscan = pscan->next; 136 free(pdel); 137 } 138 139 *plist = NULL; 140 } 141 142 /********************************************** 143 单链表翻转:采用3个指针就地翻转 144 **********************************************/ 145 void ListInvert(List *plist) 146 { 147 assert(NULL != plist); 148 149 struct node *head, *tail, *pscan; 150 151 head = NULL; 152 pscan = *plist; 153 154 while (pscan) 155 { 156 tail = head; 157 head = pscan; 158 pscan = pscan->next; 159 head->next = tail; 160 } 161 162 *plist = head; 163 } 164 165 /********************************************** 166 检查单链表是否有环: 167 采用2个指针以不同的步长移动,若有环,则快的一定 168 能追上慢的 169 **********************************************/ 170 bool ListIsLoop(const List list) 171 { 172 struct node *fast; 173 struct node *slow; 174 175 if (NULL == list) 176 return false; 177 178 slow = list; 179 fast = list->next; 180 181 while (NULL != fast) 182 { 183 if (slow == fast) 184 return true; 185 186 slow = slow->next; 187 188 fast = fast->next; 189 if (NULL == fast) 190 return false; 191 fast = fast->next; 192 } 193 194 return false; 195 } 196 197 /********************************************** 198 串接2个单链表: 199 将list2串接到list1之后,返回串接后的链表头 200 **********************************************/ 201 struct node * ListConcatenate(List list1, List list2) 202 { 203 struct node *ptemp; 204 205 if (NULL == list1) 206 return list2; 207 208 ptemp = list1; 209 while (NULL != ptemp->next) 210 ptemp = ptemp->next; 211 212 ptemp->next = list2; 213 214 return list1; 215 } 216 217 /********************************************** 218 判断两个链表是否相交: 219 将两个链表串接起来,判断是否有环 220 **********************************************/