以下**是在vs2013下編寫的:
我們先來看一下測試結果:
#include#include#include#include//鍊錶的定義
typedef int datatype;
typedef struct slistnode
slistnode;
//初始化
void slistinit(slistnode **pfirst)
//銷毀
void slistdestroy(slistnode **pfirst)
*pfirst = null;
}slistnode * createnewnode(int data)
// 尾插
void pushback(slistnode **ppfirst, datatype data)
slistnode *pnode;
pnode = *ppfirst;
while (pnode->pnext != null)
// pnode 就是倒數第乙個
pnode->pnext = pnewnode;
}// 倒敘列印鍊錶
#if 1
void reverseprint(slistnode *pfirst)
end = pnode;//依次找到最後乙個,倒數第二個·······第乙個
printf(" data);
pnode = pfirst;//讓pnode為第乙個結點,繼續找
} printf("\n");
}#endif
#if 0
void show(slistnode*p)
printf("data);
}void testprintr()
#endif
// 頭刪
void popfront(slistnode **ppfirst)
//頭插
void pushfront(slistnode **ppfirst, datatype data)
// 逆置鍊錶
#if 1
slistnode * reverselist(slistnode *pfirst)
return pnewfirst;
}#endif
slistnode * reverselist2(slistnode *pfirst)
slistnode *p1 = null;
slistnode *p2 = pfirst;//1的位址
slistnode *p3 = pfirst->pnext;//2的位址
while (p2) }
return p1;
}//查詢
slistnode *find(slistnode *pfirst,datatype data)
} return null; }
// 刪除非尾無頭鍊錶
//首先,我們先建立乙個節點pcur,令節點pcur指向要刪除的節點pos的下乙個節點,然後,我們先把pcur的值賦給pos, 然後再刪除掉pcur這個節點,
void removenodenottail(slistnode *pos)
// 無頭鍊錶前插入
void insertnohead(slistnode *ppos, int data)
/*約瑟夫環
*/slistnode * jocephcircle(slistnode *pfirst, int k)
pnode->pnext = pfirst;
//開始執行
pnode = pfirst;
while (pnode->pnext != pnode)
//刪除第k個結點
pprev->pnext = pnode->pnext;
free(pnode);
//記住讓pnode指向下乙個
pnode = pprev->pnext;
} return pnode;
}// 合併兩個有序鍊錶
slistnode * mergeorderedlist(slistnode *p1first, slistnode *p2first)
else
}//判空
slistnode *notempty = p1;
if (p1 == null)
while (notempty != null)
return pnewfirst;
}// 遍歷一次,找到中間結點
slistnode * findmid(slistnode *pfirst)
pfast = pfast->pnext;
if (pfast == null)
}return pslow;
}// 遍歷一次,找到倒數第 k 個結點(k從1開始)
slistnode * findk(slistnode *pfirst, int k)
//定義兩個指標
slistnode *p1=pfirst;//先走k-1步
slistnode *p2=pfirst;//然後兩個同時走
int i = 0;
for (i = 0; i <= k - 1; i++)
while (p1)
return p2;
}// 遍歷一次,刪除倒數第 k 個結點(k從1開始),不能用替換刪除法 ,有問題
void removek(slistnode *pfirst, int k)
slistnode *pcur=pfirst;
for (pcur = pfirst; pcur != find; pcur = pcur->pnext)
//找到find的前乙個節點位址
pcur->pnext = find->pnext;
free(find);
}// 判斷兩個鍊錶是否相交,求交集
void unionset(slistnode *pfirst1, slistnode *pfirst2)
else if (p1->data>p2->data)
else
} printf("\n");
}void print(slistnode *pfirst)
printf("null\n");
}void testslist()
else
/*printf("刪除非尾無頭鍊錶:");
slistnode *pfound2 = find(pfirst, 2);
removenodenottail(pfound2);
print(pfirst);
*/ printf("約瑟夫環 :");
slistnode *psuv = jocephcircle(pfirst, 3);
printf("%d\n",psuv->data);
//合併兩個有序鍊錶並且輸出有序
//slistnode *pfirst2;
//slistinit(&pfirst2);
//assert(pfirst2 == null);
尾插 //printf("尾插二:");
//pushback(&pfirst2, 4);
//pushback(&pfirst2, 5);
//pushback(&pfirst2, 6);
//pushback(&pfirst2, 7);
//pushback(&pfirst2, 8);
//print(pfirst2);
//printf("合併兩個有序鍊錶並且輸出有序 :");
//slistnode *pnewfirst3=mergeorderedlist(pfirst, pfirst2);
//print(pnewfirst3);
//printf("遍歷一次,找到中間結點 :");
//slistnode *pfound3 = findmid(pfirst);
//printf("%d\n", pfound3->data);
//printf("遍歷一次,找到倒數第 k 個結點(k從1開始) :");
//slistnode *pfound4 = findk(pfirst, 2);
// printf("%d\n", pfound4->data);
// //printf("遍歷一次,刪除倒數第 k 個結點(k從1開始),不能用替換刪除法 :");
// //removek(pfirst, 2);
// //print(pfirst);
//printf("求交集 :");
//unionset(pfirst, pfirst2);
//slistdestroy(&pfirst);
}
資料結構04 鏈表面試題分析
1 求單鏈表中節點的個數 迴圈遍歷,每次加一,當節點的下乙個節點為空時,迴圈結束 2 查詢單鏈表中的倒數第k個節點 先迴圈遍歷出鍊錶的總節點數 n 減去k即為正序查詢的第 n k 個節點 3 單鏈表的反轉 定義乙個空的鍊錶和頭節點 迴圈單鏈表,將單鏈表的節點按順序放入新建的鍊錶中,每次在新建鍊錶的頭...
線性結構 鏈表面試題
一 從尾到頭列印單鏈表 法一 遞迴法 void slistnoderecurreverseprint slistnode phead 法二 常規法 void slistnodetwoprint slistnode phead pend pcur 使pend前進一位 printf d pend dat...
鏈表面試題
不改變鍊錶結構,從尾到頭列印單鏈表 遞迴實現 void printlistrevers recursively plist phead printf d phead data 當鍊表非常長的時候,遞迴實現的會導致函式呼叫層級很深,可能導致呼叫棧溢位。用棧不會出現此類情況,顯然用棧實現 的魯棒性會好一...