|
20鱼币
本帖最后由 bin554385863 于 2019-7-18 15:30 编辑
- #include <stdio.h>
- #include <stdlib.h>
- /*链表结构体 */
- typedef struct Node
- {
- int value;
- struct Node *next;
- } node;
- /*创建链表 */
- node *creatlinklist(node *arg)
- {
- node *p1, *p2;
- p1 = p2 = (node *)malloc(sizeof(node));
- if (p2 != NULL)
- {
- /*输入节点的值 */
- scanf("%d ", &p2->value);
- /*新节点指针成员赋值为空 */
- p2->next = NULL;
- }
- /*以-1作为结束标志 */
- while (p2->value != -1)
- {
- /*若为空表,接入表头 */
- if (arg == NULL)
- {
- arg = p2;
- }
- /*反之接入表尾 */
- else
- {
- p1->next = p2;
- }
- p1 = p2;
- p2 = (node *)malloc(sizeof(node));
- if (p2 != NULL)
- {
- /*输入节点的值 */
- scanf("%d", &p2->value);
- p2->next = NULL;
- }
- }
- return arg;
- }
- /*输出链表的值 */
- void printarg(node *arg)
- {
- node *temp;
- temp = arg;
- while (temp != NULL)
- {
- printf("%d ", temp->value);
- temp = temp->next;
- }
- }
- int main(int argc, char const *argv[])
- {
- node *number = NULL;
- number = creatlinklist(number);
- printarg(number);
- return 0;
- }
复制代码
---------------------------------------------------------------------------
Microsoft Windows [版本 6.1.7601]
版权所有 (c) 2009 Microsoft Corporation。保留所有权利。
E:\Administrator\Documents\My C>cmd /C "c:\Users\Administrator\.vscode\extensions\ms-vscode.cpptools-0.24.0\debugAdapters\bin\WindowsDebugLauncher.exe --stdin=Microsoft-MIEngine-In-2jp1x1jj.all --stdout=Microsoft-MIEngine-Out-vkpcu5n3.f0r --stderr=Microsoft-MIEngine-Error-c1ah2wzj.cej --pid=Microsoft-MIEngine-Pid-xby5uia2.iia --dbgExe=E:\MinGW\bin\gdb.exe --interpreter=mi "
1 2 3 4 5 6 7 8 9 -1
1 2 3 4 5 6 7 8 9
E:\Administrator\Documents\My C>
-------------------------------------------------------------------------------------------------
输出链表我理解
链表的创建,脑壳痛
这段代码我翻来覆去的看,关于链表的视频,百度文档,还有手头的实体书一直在看,还是无法理解.
本帖最后由 砚堂_ 于 2019-7-18 22:39 编辑
中心思想:arg代表整个链表,指向第一个节点,p1指向链表已输入的部分的最后一个节点,p2永远指向空的新节点。在循环过程中,每次输入的值都存入p2的value,如果它不是-1,那么尚未结束,p2要保存,并且要继续输入。把p2挂接到p1的后面,就保存了p2;此时p2变成了已完成链表的最后一个节点,所以要把p1也指向p2(别忘记了p1的任务就是指向最后一个节点!),然后p2需要指向一个新的空节点(p2的任务)。接着就是下一轮循环了。
小细节:
1,按理来说arg只需要指向第一个节点,那么只要赋值一次就可以了,所以是可以写在循环体的外面的。但是如果写在外面的话,就要先找到第一个节点,并对第一个节点做特殊处理。有时特殊处理会非常复杂繁琐。所以很多情况下会设一个虚拟存在的节点放在最前面,这样原本的第一个节点就变成了第二个节点,所有的节点都处于平等的位置,做同样的处理就可以了。最后返回的时候,抛弃第一个虚拟的节点,返回第二个节点就可以了。这是代码中arg=p2而不是arg=p1的原因。
2,一般来说,链表的最后一个节点的next应该是NULL。所以在返回arg之前,把p1(p1总是指向最后一个节点!)的next赋值为NULL就可以了。但是这面临一个问题:可能p1本身就是NULL,这就需要对p1先做判断。还有一种解决办法是,强制使每次添加完新节点,p1的next都是NULL,那在返回arg之前就不必再处理链表的尾部了。具体实现就是代码中的,每次新生成的节点p2,其next先预置NULL。
|
最佳答案
查看完整内容
中心思想:arg代表整个链表,指向第一个节点,p1指向链表已输入的部分的最后一个节点,p2永远指向空的新节点。在循环过程中,每次输入的值都存入p2的value,如果它不是-1,那么尚未结束,p2要保存,并且要继续输入。把p2挂接到p1的后面,就保存了p2;此时p2变成了已完成链表的最后一个节点,所以要把p1也指向p2(别忘记了p1的任务就是指向最后一个节点!),然后p2需要指向一个新的空节点(p2的任务)。接着就是下一轮循环了。
小 ...
|