鱼C论坛

 找回密码
 立即注册
12
返回列表 发新帖
楼主: a905448839

[已解决](悬赏贴)求个大佬求助,帮我解答一下本题

[复制链接]
 楼主| 发表于 2023-6-19 10:26:17 From FishC Mobile | 显示全部楼层
本帖最后由 a905448839 于 2023-6-19 10:27 编辑
人造人 发表于 2023-6-19 10:13
没看懂,用代码说明你的问题吧


简单来说就是 在Merge函数里对传进来的L1  L2做节点位置的修改后,返回到main函数里L1 L2节点位置还是传入main函数之前的位置。但是在Merge函数里 直接对L1->Next = NULL做这个动作 是能够影响到main函数的 但是如果移动了节点做这样的动作 是无法影响到main函数的 是为什么呢?
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 10:52:23 | 显示全部楼层
对传进来的L1  L2做节点位置的修改
怎么个修改法?
返回到main函数里L1 L2节点位置还是传入main函数之前的位置
这个L1 L2节点位置是什么意思?
是L1 L2这两个指针指向的节点?还是整个链表?

但是如果移动了节点做这样的动作 是无法影响到main函数的
这个无法影响到main函数体现在哪里?

最好还是用代码说明问题,用文字叙述会有太多的变数
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 10:58:48 | 显示全部楼层
a905448839 发表于 2023-6-19 10:26
简单来说就是 在Merge函数里对传进来的L1  L2做节点位置的修改后,返回到main函数里L1 L2节点位置还是 ...

但是如果移动了节点做这样的动作 是无法影响到main函数的
可以修改呀

  1. #include <stdio.h>
  2. #include <stdlib.h>

  3. typedef int ElementType;
  4. typedef struct Node *PtrToNode;

  5. struct Node {
  6.     ElementType Data;
  7.     PtrToNode Next;
  8. };

  9. typedef PtrToNode List;

  10. void Print(List L); /* 细节在此不表;空链表将输出NULL   (同上)*/


  11. void list_free(List L) {
  12.     if(L) list_free(L->Next);
  13.     free(L);
  14. }

  15. void list_append(List L) {
  16.     while(L->Next) L = L->Next;     // 修改L,让他指向最后面
  17.     // 在最后面添加一个节点
  18.     L->Next = malloc(sizeof(*L->Next));
  19.     L->Next->Data = 456;
  20.     L->Next->Next = NULL;
  21. }

  22. int main(void) {
  23.     List L1 = malloc(sizeof(*L1));
  24.     L1->Next = malloc(sizeof(*L1->Next));
  25.     L1->Next->Data = 123;
  26.     L1->Next->Next = NULL;
  27.     Print(L1);
  28.     list_append(L1);
  29.     Print(L1);
  30.     list_free(L1);
  31.     return 0;
  32. }

  33. void Print(List L) {
  34.     List p = L->Next;
  35.     if(p) {
  36.         List r;
  37.         r = L;
  38.         while(r->Next) {
  39.             r = r->Next;
  40.             printf("%d ", r->Data);
  41.         }
  42.     } else {
  43.         printf("NULL");
  44.     }
  45.     printf("\n");
  46. }
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 11:00:58 | 显示全部楼层
  1. #include <stdio.h>
  2. #include <stdlib.h>

  3. typedef int ElementType;
  4. typedef struct Node *PtrToNode;

  5. struct Node {
  6.     ElementType Data;
  7.     PtrToNode Next;
  8. };

  9. typedef PtrToNode List;

  10. void Print(List L); /* 细节在此不表;空链表将输出NULL   (同上)*/


  11. void list_free(List L) {
  12.     if(L) list_free(L->Next);
  13.     free(L);
  14. }

  15. void list_append(List L, ElementType v) {
  16.     while(L->Next) L = L->Next;     // 修改L,让他指向最后面
  17.     // 在最后面添加一个节点
  18.     L->Next = malloc(sizeof(*L->Next));
  19.     L->Next->Data = v;
  20.     L->Next->Next = NULL;
  21. }

  22. int main(void) {
  23.     List L1 = malloc(sizeof(*L1));
  24.     L1->Next = NULL;
  25.     Print(L1);
  26.     list_append(L1, 123);
  27.     Print(L1);
  28.     list_append(L1, 456);
  29.     Print(L1);
  30.     list_free(L1);
  31.     return 0;
  32. }

  33. void Print(List L) {
  34.     List p = L->Next;
  35.     if(p) {
  36.         List r;
  37.         r = L;
  38.         while(r->Next) {
  39.             r = r->Next;
  40.             printf("%d ", r->Data);
  41.         }
  42.     } else {
  43.         printf("NULL");
  44.     }
  45.     printf("\n");
  46. }
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2023-6-19 13:24:33 | 显示全部楼层

写了个代码开验证  代码后面的备注是我错误的理解
我发现直接用传入函数的指针做移动 假设这个指针是p 无论移动到哪里或者不移动
对p做修改是无效的 比如p=NULL 但是对p->Next的修改是有效的 比如p->Next = NULL;

代码1对指针p直接做修改 无效:
  1. #include<stdio.h>
  2. #include <stdlib.h>

  3. struct sum {
  4.     int a;
  5.     struct sum  *Next;
  6. };

  7. struct sum* read( struct sum  *p);
  8. void print(struct sum  *p);
  9. void move( int i, struct sum  *p);//把这个链表第i个结构体里的下一个结构体指针设为NULL
  10. void Nomove(struct sum  *p);

  11. struct sum* read(struct sum* p)
  12. {
  13.     int i = 10;
  14.     struct sum* head = p;
  15.     while (i)
  16.     {
  17.         p->a = i;
  18.         if (i == 1)
  19.             p->Next = NULL;
  20.         else
  21.             p->Next = (struct sum*)malloc(sizeof(struct sum));
  22.             
  23.         p = p->Next;
  24.         i--;
  25.     }
  26.     return head;
  27. }
  28. void print(struct sum  *p)
  29. {
  30.         printf("此时链表为:head->");
  31.         while(p)
  32.         {
  33.                 printf("%d->",p->a);
  34.                 p = p->Next;
  35.         }
  36.         printf("NULL\n");
  37. }

  38. void move(int i, struct sum  *p)//把这个链表第i个结构体里的下一个结构体指针设为NULL
  39. {
  40.         i = i-1;
  41.         while(i--)
  42.         p = p->Next; //直接用传进来的指针做移动节点

  43.         p = NULL;
  44. //        p->Next = NULL;

  45.         //移动到i的位置后让p指向NULL 即i的位置p->Next = NULL
  46.         //但是结束后回到main函数并没有影响整个链表
  47.         //但是如果不移动节点 直接让传进来的指针为NULL 也不返回这个指针 能够影响到main函数的链表
  48.         //如下
  49.        
  50. }

  51. void Nomove(struct sum  *p)
  52. {
  53.         p = NULL;       
  54. //        p->Next = NULL;
  55.        
  56. }

  57. int main(void)
  58. {
  59.         struct sum *p;
  60.         p = (struct sum*)malloc(sizeof(struct sum));
  61.         p = read(p);
  62.         print(p);
  63.        
  64.         move(4,p);
  65.         print(p);

  66.         Nomove(p);
  67.         print(p);

  68.         return 0;
  69. }
复制代码

2d0ed444b832446ccc71c9bd2372b99.png
代码2对指针p->Next做修改 有效:
  1. #include<stdio.h>
  2. #include <stdlib.h>

  3. struct sum {
  4.     int a;
  5.     struct sum  *Next;
  6. };

  7. struct sum* read( struct sum  *p);
  8. void print(struct sum  *p);
  9. void move( int i, struct sum  *p);//把这个链表第i个结构体里的下一个结构体指针设为NULL
  10. void Nomove(struct sum  *p);

  11. struct sum* read(struct sum* p)
  12. {
  13.     int i = 10;
  14.     struct sum* head = p;
  15.     while (i)
  16.     {
  17.         p->a = i;
  18.         if (i == 1)
  19.             p->Next = NULL;
  20.         else
  21.             p->Next = (struct sum*)malloc(sizeof(struct sum));
  22.             
  23.         p = p->Next;
  24.         i--;
  25.     }
  26.     return head;
  27. }
  28. void print(struct sum  *p)
  29. {
  30.         printf("此时链表为:head->");
  31.         while(p)
  32.         {
  33.                 printf("%d->",p->a);
  34.                 p = p->Next;
  35.         }
  36.         printf("NULL\n");
  37. }

  38. void move(int i, struct sum  *p)//把这个链表第i个结构体里的下一个结构体指针设为NULL
  39. {
  40.         i = i-1;
  41.         while(i--)
  42.         p = p->Next; //直接用传进来的指针做移动节点

  43. //        p = NULL;
  44.         p->Next = NULL;

  45.         //移动到i的位置后让p指向NULL 即i的位置p->Next = NULL
  46.         //但是结束后回到main函数并没有影响整个链表
  47.         //但是如果不移动节点 直接让传进来的指针为NULL 也不返回这个指针 能够影响到main函数的链表
  48.         //如下
  49.        
  50. }

  51. void Nomove(struct sum  *p)
  52. {
  53. //        p = NULL;       
  54.         p->Next = NULL;
  55.        
  56. }

  57. int main(void)
  58. {
  59.         struct sum *p;
  60.         p = (struct sum*)malloc(sizeof(struct sum));
  61.         p = read(p);
  62.         print(p);
  63.        
  64.         move(4,p);
  65.         print(p);

  66.         Nomove(p);
  67.         print(p);

  68.         return 0;
  69. }
复制代码


386863bd77c1d828723b4cb65e87f08.png

为什么对p指针目前所指向的结构体做修改不行  对它下一个节点做修改却有效?
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2023-6-19 13:32:49 | 显示全部楼层

我想用一个二级指针a指向指针p

这样通过         *a = NULL; 来修改还是无法改变结果。。


  1. void Nomove(struct sum  *p)
  2. {
  3. //        p = NULL;       
  4. //        p->Next = NULL;
  5.        
  6.          struct sum** a = &p;
  7.          
  8.          *a = NULL;
  9. }
复制代码


8a1f4412bc5dfbd46fbeacb966b1f0c.png
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 17:23:42 | 显示全部楼层
a905448839 发表于 2023-6-19 13:24
写了个代码开验证  代码后面的备注是我错误的理解
我发现直接用传入函数的指针做移动 假设这个指针是p  ...

一个是修改指针的指向
一个是修改指针指向的值
这两个是不一样的,你需要好好理解一下这两个的不同

  1. #include <stdio.h>

  2. int main(void) {
  3.     int a = 123;
  4.     int b = 456;
  5.     int *p = NULL;
  6.     p = &a;         // 修改指针p的指向
  7.     *p = 789;       // 修改指针p指向的值
  8.     p = &b;         // 修改指针p的指向
  9.     *p = 100;       // 修改指针p指向的值
  10.     printf("%d %d\n", a, b);
  11.     return 0;
  12. }
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 17:28:21 | 显示全部楼层
a905448839 发表于 2023-6-19 13:32
我想用一个二级指针a指向指针p

这样通过         *a = NULL; 来修改还是无法改变结果。。

你这修改的是指针的指向,不是指针指向的值

  1. sh-5.1$ cat main.c
  2. #include <stdio.h>

  3. int b = 456;

  4. void func(int *p) {
  5.     int **x = &p;
  6.     *x = &b;        // 修改指针p的指向
  7.     **x = 789;      // 修改指针p指向的值
  8. }

  9. int main(void) {
  10.     int a = 123;
  11.     func(&a);
  12.     printf("%d %d\n", a, b);
  13.     return 0;
  14. }
  15. sh-5.1$ ./main
  16. 123 789
  17. sh-5.1$
复制代码
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2023-6-19 17:50:11 | 显示全部楼层
不用gpt,hehe
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2023-6-20 00:08:11 From FishC Mobile | 显示全部楼层
人造人 发表于 2023-6-19 17:23
一个是修改指针的指向
一个是修改指针指向的值
这两个是不一样的,你需要好好理解一下这两个的不同

谢谢!!
小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-6-10 05:20

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表