Question: C语言错误 : free(): invalid next size (fast): 0x0000000000c34030

引用 5 楼 张博约 的回复:1.   指针数组 'ret' 越界了； 2.   calloc分配的内存的大小等于两个参数之积， 第二个参数为0时该接口的行为不明确，具体取决于库的实现； 3.  【建议】 如果要以‘|’为分界符拆分字符串，可以看看strtok 接口。 根据大佬所说，特意去看了下calloc函数的功能，以前的错误理解函数功能以及参数，正确的定义应该为：void *calloc(size_t nmemb, size_t size); 现做修改如下： 1、将上面程序中所有calloc函数的第二参数修改为“sizeof(char *)或者sizeof(char **)”； 2、将上面程序中 ret = (char **)calloc(sizeof(char **), 0); 修改成  ret = (char **)calloc(sizeof(char **) * strLen, sizeof(char **)); 这样即可正常运行了。

引用 3 楼 真相重于对错 的回复:而且你的代码有内存泄露 因为ret是二级指针，所以他相当于一个指针数组，其中每个元素都是指针，要释放ret之前，还要释放它所包含每个指针。 按照大佬的说明修改代码，增加了二级指针的内存大小，增加了malloc与free的匹配的程序，现在修改成了下面这样： #include <stdio.h> #include <stdlib.h> #include <string.h> #include <time.h>  int main(int argc, const char **argv) {     char *srcStr = "1111|22222|100.215|false|00000000|000.003|00100|00122|00133";     char *srcTmp = srcStr;      char idx = '|';       int strLen = strlen(srcStr);     char *tmp = (char *)calloc(sizeof(char) * (strLen + 1), 0);     char **ret = NULL;      ret = (char **)calloc(sizeof(char **) * 10, 0);      printf("line = %d, ret    = %p, malloc = %ld\n", __LINE__, ret, sizeof(char **));      int i = 0;     while ((tmp = strchr(srcTmp, idx)) != NULL)     {          ret[i] = malloc(sizeof(char) * (strLen + 1));         memset(ret[i], 0, sizeof(char) * (strLen + 1));         strncpy(ret[i], srcTmp, strlen(srcTmp) - strlen(tmp));         printf("line = %d, ret[%d] = %p, malloc = %ld, %s, %ld, %ld\n",             __LINE__, i, ret[i], sizeof(char) * (strLen + 1), ret[i],             strlen(srcTmp), strlen(tmp));         srcTmp = tmp + 1;         i++;     }     ret[i] = malloc(sizeof(char) * (strLen + 1));     memset(ret[i], 0, sizeof(char) * (strLen + 1));     strncpy(ret[i], srcTmp, strlen(srcTmp));     printf("line = %d, ret[%d] = %p, malloc = %ld, %s\n", __LINE__,          i, ret[i], sizeof(char) * (strLen + 1), ret[i]);      for(int j = 0; j < i; j++)     {         free(ret[j]);         printf("Line = %d, free(ret[%d] = %p\n", __LINE__, j, ret[j] );         ret[j] = NULL;     }     free(tmp);     free(ret);      return 0; }  运行的结果为： $ ./a.out   line = 17, ret    = 0x1c4b030, malloc = 8 line = 26, ret[0] = 0x1c4b460, malloc = 60, 1111, 59, 55 line = 26, ret[1] = 0x1c4b4b0, malloc = 60, 22222, 54, 49 line = 26, ret[2] = 0x1c4b500, malloc = 60, 100.215, 48, 41 line = 26, ret[3] = 0x1c4b550, malloc = 60, false, 40, 35 line = 26, ret[4] = 0x1c4b5a0, malloc = 60, 00000000, 34, 26 line = 26, ret[5] = 0x1c4b5f0, malloc = 60, 000.003, 25, 18 line = 26, ret[6] = 0x1c4b640, malloc = 60, 00100, 17, 12 line = 26, ret[7] = 0x1c4b690, malloc = 60, 00122, 11, 6 line = 34, ret[8] = 0x1c4b6e0, malloc = 60, 00133 Line = 40, free(ret[0] = 0x1c4b460 Line = 40, free(ret[1] = 0x1c4b4b0 Line = 40, free(ret[2] = 0x1c4b500 Line = 40, free(ret[3] = 0x1c4b550 段错误 (核心已转储)

引用 楼主 smartergirl 的回复:本人小白首先向各位大佬们致敬！祝大佬们哪哪都好！ 本人小白在学习C语言指针的时候遇到了一个比较难的问题，目前已经处于无处下爪的阶段，特来向各位大佬请教！ 下面是本人编写的代码，在运行过程中会出现如题错误。 #include <stdio.h> #include <stdlib.h> #include <string.h> #include <time.h>  int main(int argc, const char **argv) {     char *srcStr = "1111|22222|100.215|false|00000000|000.003|00100|00122|00133";     char *srcTmp = srcStr;     char idx = '|';       int strLen = strlen(srcStr);     char *tmp = (char *)calloc(sizeof(char) * (strLen + 1), 0);     char **ret = NULL;      ret = (char **)calloc(sizeof(char **), 0);      printf("line = %d, ret = %p, malloc = %ld\n", __LINE__, ret, sizeof(char **));      int i = 0;     while ((tmp = strchr(srcTmp, idx)) != NULL)     {          ret[i] = malloc(sizeof(char) * (strLen + 1));         memset(ret[i], 0, sizeof(char) * (strLen + 1));         strncpy(ret[i], srcTmp, strlen(srcTmp) - strlen(tmp));         printf("line = %d, ret[%d] = %p, malloc = %ld, %s, %ld, %ld\n",             __LINE__, i, ret[i], sizeof(char) * (strLen + 1), ret[i],             strlen(srcTmp), strlen(tmp));         srcTmp = tmp + 1;         i++;     }     ret[i] = malloc(sizeof(char) * (strLen + 1));     memset(ret[i], 0, sizeof(char) * (strLen + 1));     strncpy(ret[i], srcTmp, strlen(srcTmp));     printf("line = %d, ret[%d] = %p, malloc = %ld, %s\n", __LINE__,          i, ret[i], sizeof(char) * (strLen + 1), ret[i]);     free(tmp);     free(ret);      return 0; } 使用系统为Ubuntu 16.04 LTS，编译为 gcc version 5.4.0 20160609 (Ubuntu 5.4.0-6ubuntu1~16.04.10) 下面是错误的提示信息： $ ./a.out  line = 20, ret = 0x1881030, malloc = 8 line = 29, ret[0] = 0x1881460, malloc = 58, 1111, 57, 53 line = 29, ret[1] = 0x18814b0, malloc = 58, 22222, 52, 47 line = 29, ret[2] = 0x1881500, malloc = 58, 100215, 46, 40 line = 29, ret[3] = 0x1881550, malloc = 58, false, 39, 34 line = 29, ret[4] = 0x18815a0, malloc = 58, 00000000, 33, 25 line = 29, ret[5] = 0x18815f0, malloc = 58, 000003, 24, 18 line = 29, ret[6] = 0x1881640, malloc = 58, 00100, 17, 12 line = 29, ret[7] = 0x1881690, malloc = 58, 00122, 11, 6 line = 37, ret[8] = 0x18816e0, malloc = 58, 00133 *** Error in `./a.out': free(): invalid next size (fast): 0x0000000001881030 *** ======= Backtrace: ========= /lib/x86_64-linux-gnu/libc.so.6(+0x777e5)[0x7f0ce19667e5] /lib/x86_64-linux-gnu/libc.so.6(+0x8037a)[0x7f0ce196f37a] /lib/x86_64-linux-gnu/libc.so.6(cfree+0x4c)[0x7f0ce197353c] ./a.out[0x400a01] /lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xf0)[0x7f0ce190f830] ./a.out[0x400659] ======= Memory map: ======== 00400000-00401000 r-xp 00000000 08:07 664382                             /home/songtb/Desktop/debug/a.out 00600000-00601000 r--p 00000000 08:07 664382                             /home/songtb/Desktop/debug/a.out 00601000-00602000 rw-p 00001000 08:07 664382                             /home/songtb/Desktop/debug/a.out 01881000-018a2000 rw-p 00000000 00:00 0                                  [heap] 7f0cdc000000-7f0cdc021000 rw-p 00000000 00:00 0  7f0cdc021000-7f0ce0000000 ---p 00000000 00:00 0  7f0ce16d9000-7f0ce16ef000 r-xp 00000000 08:01 396993                     /lib/x86_64-linux-gnu/libgcc_s.so.1 7f0ce16ef000-7f0ce18ee000 ---p 00016000 08:01 396993                     /lib/x86_64-linux-gnu/libgcc_s.so.1 7f0ce18ee000-7f0ce18ef000 rw-p 00015000 08:01 396993                     /lib/x86_64-linux-gnu/libgcc_s.so.1 7f0ce18ef000-7f0ce1aaf000 r-xp 00000000 08:01 396955                     /lib/x86_64-linux-gnu/libc-2.23.so 7f0ce1aaf000-7f0ce1caf000 ---p 001c0000 08:01 396955                     /lib/x86_64-linux-gnu/libc-2.23.so 7f0ce1caf000-7f0ce1cb3000 r--p 001c0000 08:01 396955                     /lib/x86_64-linux-gnu/libc-2.23.so 7f0ce1cb3000-7f0ce1cb5000 rw-p 001c4000 08:01 396955                     /lib/x86_64-linux-gnu/libc-2.23.so 7f0ce1cb5000-7f0ce1cb9000 rw-p 00000000 00:00 0  7f0ce1cb9000-7f0ce1cdf000 r-xp 00000000 08:01 396927                     /lib/x86_64-linux-gnu/ld-2.23.so 7f0ce1ebc000-7f0ce1ebf000 rw-p 00000000 00:00 0  7f0ce1edd000-7f0ce1ede000 rw-p 00000000 00:00 0  7f0ce1ede000-7f0ce1edf000 r--p 00025000 08:01 396927                     /lib/x86_64-linux-gnu/ld-2.23.so 7f0ce1edf000-7f0ce1ee0000 rw-p 00026000 08:01 396927                     /lib/x86_64-linux-gnu/ld-2.23.so 7f0ce1ee0000-7f0ce1ee1000 rw-p 00000000 00:00 0  7ffe87400000-7ffe87421000 rw-p 00000000 00:00 0                          [stack] 7ffe8751c000-7ffe8751f000 r--p 00000000 00:00 0                          [vvar] 7ffe8751f000-7ffe87521000 r-xp 00000000 00:00 0                          [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0                  [vsyscall] 已放弃 (核心已转储)   小白，积分不多，已经全部上缴了。。。。。  malloc和free成对使用  只看到ret[i] = malloc(sizeof(char) * (strLen + 1)); 没有看到free(ret[i])呀

你这个肯定不对 ret 是一个二级指针，你只alloc了一个元素，然后你又用ret[i]方式写入了好多元素，所以free的时候要出错

顺便说一下，在有一些情况下是可以正常运行的。比如这样的情况下： 1、将上面的代码中第10行中` char idx = '|';   ` 修改成  ` char idx = '.';   `，那么就可以正常运行，运行结果为： $ ./a.out  line = 17, ret = 0x1676030, malloc = 8 line = 26, ret[0] = 0x1676460, malloc = 60, 1111|22222|100, 59, 45 line = 26, ret[1] = 0x16764b0, malloc = 60, 215|false|00000000|000, 44, 22 line = 34, ret[2] = 0x1676500, malloc = 60, 003|00100|00122|00133


Question: 约瑟夫环（C语言单循环链表实现）

#include<stdio.h> #include<stdlib.h> #include<string.h>  struct node {     int num;     char name[20];     struct node *next; };  struct node *create_singly_link(int num) {     struct node *head, *prev, *cur;     int i;      head = NULL;     for(i = 0; i < num; i++) {         cur = (struct node *)malloc(sizeof(struct node));         if (!cur) {             printf("Malloc error!");             return NULL;         }         cur->next = NULL;         cur->num = i+1;         snprintf(cur->name, 20-1, "%c", 'A'+i);         if (!head) {             head = cur;             prev = cur;         } else {             prev->next = cur;             prev = prev->next;         }     }     prev->next = head;     return head; }  static void test_print(struct node *phead) {     struct node *pcur = phead->next;      printf("num = %d\t name = %s\n", phead->num, phead->name);     while (pcur != phead) {         printf("num = %2d\t name = %s\n", pcur->num, pcur->name);         pcur = pcur->next;     } }  int output( struct node *head, int start, int step, int total) {     struct node *p, *q;     int count = 0;     int num = 0, i;      q = head;      for(i = 0; i < start; i++)         q = q->next;      while(count < total-1) {         p = q->next;         num++;         if(!(num % step)) {             q->next = p->next;             printf("%s\n", p->name);             free(p);             count++;         } else {             q = p;         }     }     printf("num = %d\t, name = %s\n", q->num, q->name);     free(q);      return 0; } int main(int argc, const char *argv[]) {     int total, step, start;     struct node *head;      printf("Please input total test number: ");     scanf("%d", &total);     head = create_singly_link(total);     test_print(head);      printf("Please input start position and steps: ");     scanf("%d%d", &start, &step);      output(head, start, step, total);      return 0; } 供参考～

使用链表的话，不适合用带有空表头的实现。因为表尾要指向第一个有意义的数据，而且第一个位置也有可能被删除。 表头不含实际数据的话，就有两个指针指向第一个数据，容易操作不方便实现。   主体程序大抵如此：   #include <stdio.h> #include <stdlib.h>  typedef struct Node {     int data;     struct Node *next; } Node;  static void debug_print_list(struct Node *l);  Node* Init(int n) {     int i;     Node *node, *head = NULL, *prev = NULL;      for(i = 0; i < n; i++) {         node = (Node*) malloc(sizeof(Node));         node->data = i;         node->next = NULL;          if (head == NULL) {             head = node;         }          if (prev != NULL) {             prev->next = node;         }         prev = node;     }     prev->next = head;      return head; }  Node *Order(Node *L, int n, int m) {     Node *p = NULL, *q = L;  // p points to previous node, q points to current node     int counter = 0;      while (1) {         if (q->next == q)             break;          counter += 1;         printf("[DBEUG]: node %d reports %d\n", q->data, counter);         if (counter == m) {             // assert(p != NULL); corner case need to be considered             printf("[DEBUG]: Removing node %d\n", q->data);             p->next = q->next;             free(q);             q = p->next;              counter = 0;             debug_print_list(q);             continue;         }          p = q;         q = q->next;     }      return q; }  int main() {     Node* L, *result;     int n,m;     n = 9;     m = 3;      L=Init(n);     debug_print_list(L);      result = Order(L, n, m);     printf("n=%d, m=%d, final-node=%d\n", n, m, result->data);     return 0; }  void debug_print_list(Node *l) {     Node *p = l;      while (1) {         printf("%d", p->data);         if (p->next != l)             printf(" --> ");         p = p->next;          if (p == l)             break;     };      printf("\n"); }

typedef的一般用法是兩個不同的名字，比如typedef _Node { ... } Node; malloc分配内存後，應該判斷返回是否NULL，否則對其操作可能出錯 Init函數中對首節點的處理也有問題，當n為1時，p->next=q會導致鏈表不是以NULL結尾


Question: 函数调用

引用 1 楼 user-1的回复:return(arry[i]); 这一句相当于 return array[9],它的作用是什么呢？ 我懂了，谢谢

引用 1 楼 user-1的回复:return(arry[i]); 这一句相当于 return array[9],它的作用是什么呢？ 可以不用这个吗，我小白，大佬


Question: 中序线索化二叉树算法使用顺序栈

StackInitiate函数的代码呢？ 看参数StackInitiate(&st)是二级指针，估计函数内部是动态分配内存（说明顺序栈的大小是动态的）。所以最后要释放内存。

这个是一个伪代码。 释放的是栈 st的空间，StackInitiate(&st) 和 free(st) 对应。 栈内存储的只是指针，也没有对应的free。

书写错  下一题


Question: 农夫过河问题

类似于i+=1; i+=1; i=i+; ======= m<<=1; 相当于 m=m<<1;

引用 1 楼 真相重于对错的回复:左移一位，相当于乘2 为什么还要加个等号，直接movers＜＜1这样可以吗

这是位运算，<<是左移，>>是右移，是对二进制的操作 和一般运算符操作一样，比如+，+1表示加1，变量+=1就是变量+1的结果再赋给变量 同理，<<1表示左移1位，变量<<=1就是变量左移1位的结果再赋给变量 因为是二进制，所以左移1位相当于乘2，右移1位相当于除以2， 比如，移1个字节8位bit来举例，二进制00000001（十进制 1），左移1位变成00000010（十进制 2），高位舍弃低位补0，十进制从1变成2，相当于乘2。

左移一位，相当于乘2


Question: 字符串处理的常用库函数

使用  其他   字符串处理库函数 时   在  C源程序 中包含  头文件string.h  楼主的语文是体育老师教的。  老婆给当程序员的老公打电话：下班顺路买十个包子，如果看到卖西瓜的，买一个。当晚老公手捧一个包子进了家门…老婆怒道：你怎么只买一个包子?!老公甚恐，喃喃道：因为我真看到卖西瓜的了。

就是在使用字符串处理函数时，需要包含头文件string.h，因为这个头文件里包含了字符串处理函数的声明，库函数实现在动态库里（这个不需要关心），只需要引入头文件就好了。

你是学语文还是学编程？这句话在文法上其他的字符串处理函数和其他字符串处理的函数都说得通，但是如果你会编程，就不会问这种奇葩的问题。 就好比医学生不会对“变态反应”大惊小怪。

纠正一下，字符串处理是函数的定语

这是中文理解的歧义吗？ 其他字符串处理库函数 的正确理解是 其他字符串处理库函数   ，关键词就是其他函数，其他的什么函数呢？字符串处理函数 所以，不是其他字符串，是其他函数，字符串处理是函数的定于。  感觉想再教语文。。。


Question: Strassen算法代码：内存出错，求大佬指点，马上交报告了

引用 2 楼 Anthony.F.Young 的回复:救救孩子！！！（捞一下寄几）  1.建议free后，直接将指针置为NULL 否则如果重复释放，不好判定。 2. 不要在一行放多个语句，影响定位问题。  在出错的地方下断点看一下。 基本就是空指针或者溢出的问题

释放空指针了吧， 怎么分配的内存空间啊， 去分配的地方仔细检查一下吧

大佬们帮帮忙呀

救救孩子！！！（捞一下寄几）

楼主是上海某985大二学渣，算法课让实现矩阵规模非2的幂次下的strassen算法，搞来搞去好像都是内存方面的错误，烦请各位大佬帮我看看哪儿的问题


Question: 农夫过河问题

0x开头是16进制，但是&运算没有规定必须用二进制啊，只是运算过程用二进制来运算 比如 int a = 5, b = 3; int c = a & b; //操作数都是10进制，5 是 101， 3 是 011，所以 5&3=101&011=001=1（十进制），运算过程用二进制，操作数没有规定必须用二进制，所以用16进制也没问题，运算过程把16进制转成2进制来运算。 16进制的0x08就是2进制的00001000，10进制是8，所以 location&0x08 和 location&8是一样的（十进制），location&1000就不对了，因为二进制不能直接表示，1000就是10进制的1000。

C语言没有你所说的二进制输入，最多可用函数去实现。 C语言本身支持的三种输入是： 1. 十进制。比如20,457； 2. 十六进制，以0x开头。比如0x7a； 3. 八进制，以0开头。比如05,0237

二进制和十六进制有区别吗？


Question: 求大佬帮我看看这两种算法的优劣

之所以说是理论上，是从出栈入栈的角度讨论的，实际上栈也是模拟的，root = stack[top--]; 或者直接 root = root->left; （不入栈）都是等效的 所以两个算法的时间复杂度和空间复杂度是一样的。

理论上算法二优越一些。 因为算法二只有一个父节点入栈，而算法一是左右两个节点都入栈（虽然左节点入栈后马上在下一轮循环出栈，但也是多了一次入栈出栈的操作）


Question: 大佬们，这个冒泡排序还有什么问题？

i是不确定值，栈上的空间不像堆上的空间可以动态指定（申请），栈上的空间需要运行前指定。

引用 3 楼 lin5161678的回复:i垃圾值 不能做数组大小 你想用输入做数组大小 得在输入语句后面这数组定义 并且你输入是n 应该用n 而不是i 万分感谢！！！

引用 1 楼 user-3的回复:最好是把代码粘上来，截图看着太累。 int a[i]感觉应该是int a[n]，但理论上c语言是不支持这样声明数组的，数组的长度必须是一个确定的常量值。 定义数组长度可以是变量

引用 1 楼 user-3的回复:最好是把代码粘上来，截图看着太累。 int a[i]感觉应该是int a[n]，但理论上c语言是不支持这样声明数组的，数组的长度必须是一个确定的常量值。 虽然改了a【i】，改用malloc后对了，但C99不是支持这样定义吗


Question: C语言|编译过了，但是测试集过不了，应该是文件读出有点问题

现在知道怎末改了吗

引用 2 楼 自信男孩 的回复:读写方式不对，读是用二进制，而写是用ascii。所以写入的内容，读出来的不一致。 建议用fscanf/fprintf或fread/fwrite进行读写

题目呢


Question: 算第m个到第n个质数的和，为啥这个for循环程序算出来是错的？

#include <stdio.h> /* 1、注意缩进 {} 2、注意t=1和t==1的区别, t==1 3、注意初始化变量 sum=0 4、注意标志变量的刷新赋值 t=1 5、注意变量的初始值 cnt=m 6、注意不同的条件可能会产生副作用 for (x = 2; cnt < n; x++)--for (i = 2; i < x; i++) */ int main() {     int x = 0, m = 0, n = 0, sum = 0, t = 1;     int cnt = 0;     scanf("%d %d", &m, &n);     cnt = m;//从m开始，否则会从0开始的     if (m > 0 && m < n && m <= 200)     {         for (x = 2; cnt < n; x++)//m~n-1之间的质数，不包括n         {             int i = 0;             t = 1;//t=1要在这里重新赋值为1             for (i = 2; i < x; i++)//2会被过滤掉，但是刚好2也是质数             {                 if (x % i == 0)                 {                     t = 0;                     break;                 }             }             if (t == 1)//原来是“t=1”             {                 if (cnt >= m)                 {                     printf("%x\n",x);                     sum += x;                 }             }             cnt++;//cnt在这里加1         }         printf("%d\n", sum);     }//注意缩进     return 0; }

#include <stdio.h> #include <math.h> /* 计算第m个质数到第n个质数之间的和 1、先计算出质数 2、取对应的质数累加求和 */ int prime(int m ,int n) {     int index = 1;     int i = 0, j = 0;     int sum = (m==1?2:0);     for (i = 3;; i++)     {         for (j = 2; j <= sqrt(i); j++)         {             if (i % j == 0)             {                 break;             }         }         if (j > sqrt(i))         {             index++;             if (index >= m && index <= n)             {                 sum += i;             }             if (index >= n)             {                 break;             }         }     }     return sum; } int main() {     int m = 0, n = 0, sum = 0;     scanf("%d %d", &m, &n);     if (m > 0 && m < n && m <= 200)     {         sum=prime(m, n);         printf("%d\n", sum);     }     return 0; }

参考一下吧  int main() {     int i, x, m, n, cnt=0, sum=0;     scanf("%d%d", &m, &n);     for (x=2; cnt<n; x+=(x==2?1:2)) {         for(i=3; i<=x/2; i+=2) {             if (x%i==0) break;         }         if (i>x/2) {             cnt++;             if (cnt>=m) {                 sum += x;             }         }     }     printf("%d\n", sum); }


Question: 求大佬帮我讲解这段代码

所谓 万变不离其宗 链表一般是单节点对单节点的单向关系（当然也有双向关系，就是双向链表） 二叉树就是单节点对双节点的单向关系（所以单向关系就是父节点能找到子节点，但子节点不能找到父节点） 图就是多节点对多节点的多向关系 所以关系越复杂，就越不好理解。（感觉怎么和生活一样）

十分感谢，我感觉二叉树代码好长，有点不好理解，但理解过后就发现其实二叉树就是链表，想想前面刚学链表时还挺轻松的，真让我郁闷

其实说好理解也好理解，说不好理解也不好理解，前中后序只是打印的地方不同，遍历过程是相同的。 就像上次跟你说的，它的遍历过程就是先找到左子树的最右节点，然后让最右节点的右节点指向父节点，然后父节点的左子树继续遍历，当遍历到最右节点的右节点就会回到父节点（因为之前设置了最右节点的右节点指向父节点），然后恢复最右节点的右节点为NULL，并遍历父节点的右子树。 所以前中后序的差别上只是在于什么时候打印。  后序打印为什么会复杂呢？因为它要遍历到最右节点才开始打印（前序，中序在中间就打印），所以它要遍历到最右节点以后，才开始逆向打印之前的各层的节点。那么怎么逆向打印呢？想想还不简单吗？因为遍历到最右节点时，最右节点的右节点又回到了父节点，拿到父节点，就可以得到原来的父节点的左右节点。 所以addPath就是为了打印这个从最右节点开始逆向遍历的结果。 先顺着打印 res[(*returnSize)++] = root->val;  root = root->right;  再逆向重新排列结果 int t = res[i]; res[i] = res[j]; res[j] = t; 这里的逆序addPath可能用了技巧，只需要对半逆向，具体没太细研究，大体思路就是这样，所以后序需要找到最右才能开始打印，不像前序中序在遍历过程中就能打印，所以它比较繁琐。 这种技巧性的东西，我觉得没有必要研究得太深，意义不大，可能只是一开始惊叹一下这技巧不错，但是不能给其他问题带来什么新的启发，所以大概了解就可以了。

大佬们，我发现二叉树的后序遍历的非递归代码相比前序遍历和中序遍历，很不好理解，有什么诀窍吗？


Question: 有大神帮忙看看嘛，最后总是输出不了啊

仅供参考：//链表实现一元多项式的加法减法乘法 #include <stdio.h> #include <stdlib.h> typedef struct node { 	float coef;	  //系数 	int	expn;	  //指数 	struct node	*next; } PolyNode;	   //多项式节点	polynomial node typedef PolyNode* Polynomial; Polynomial createPolynomial() {  //创建多项式 	PolyNode *p, *q, *head = (PolyNode *)malloc(sizeof(PolyNode));	 //头节点 	head->next = NULL; 	float coef; 	int	expn; 	printf("输入该多项式每一项的系数和指数，每项一行，输入0 0结束！\n"); 	while (scanf("%f %d", &coef, &expn) && coef) {   // 默认，按指数递减排列 		if (head->next)	{ 			p =	head; 			while (p->next && expn < p->next->expn) 				p =	p->next; 			if (p->next) { 				if (expn ==	p->next->expn) { //有相同指数的直接把系数加到原多项式 					p->next->coef += coef; 					if (p->next->coef >	-0.000001 && p->next->coef < 0.000001) { //若是相加后系数为0，则舍弃该节点 						q =	p->next; 						p->next	= q->next; 						free(q); 					} 				} else { 					q =	(PolyNode*)malloc(sizeof(PolyNode)); 					q->coef	= coef; 					q->expn	= expn; 					q->next	= p->next; 					p->next	= q; 				} 			} else { 				p->next	= (PolyNode*)malloc(sizeof(PolyNode)); 				p =	p->next; 				p->coef	= coef; 				p->expn	= expn; 				p->next	= NULL; 			} 		} else { 			head->next = (PolyNode*)malloc(sizeof(PolyNode)); 			head->next->coef = coef; 			head->next->expn = expn; 			head->next->next = NULL; 		} 	} 	return head; } Polynomial multiply(Polynomial poly, float coef, int expn) {  //多项式与指定单项式相乘，该单项式为 coefx^expn 	PolyNode *p, *q, *Poly = (PolyNode*)malloc(sizeof(PolyNode)); 	p =	Poly; 	q =	poly->next; 	while (q) { 		p->next	= (PolyNode*)malloc(sizeof(PolyNode)); 		p =	p->next; 		p->coef	= (q->coef*coef); 		p->expn	= (q->expn + expn); 		q =	q->next; 	} 	p->next	= NULL; 	return Poly; } void add(Polynomial	poly1, Polynomial poly2) {	//把 poly2 加到	poly1 上 	PolyNode *p, *q, *r; 	r =	poly1; 	p =	poly1->next;  //指向第一个节点 	q =	poly2->next; 	poly2->next	= NULL; 	while (p &&	q) { 		if (p->expn	> q->expn) { 			r->next	= p; 			p =	p->next; 			r =	r->next; 		} else if (p->expn < q->expn) { 			r->next	= q; 			q =	q->next; 			r =	r->next; 		} else { 			PolyNode *t; 			p->coef	+= q->coef; 			if (!(p->coef >	-0.000001 && p->coef < 0.000001)) //系数不为0 			{ 				r->next	= p; 				r =	r->next; 				p =	p->next; 			} else { 				t =	p; 				p =	p->next; 				free(t); 			} 			t =	q; 			q =	q->next; 			free(t); 		} 	} 	if (p) 		r->next	= p; 	if (q) 		r->next	= q; } Polynomial polySubtract(Polynomial poly1, Polynomial poly2)	{  //多项式减法	poly1-poly2形成一个新的多项式 	//把poly2的系数取相反数，形成一个新的多项式 	Polynomial poly	= (PolyNode*)malloc(sizeof(PolyNode)); //构造头节点 	PolyNode *p, *q; 	p =	poly; 	q =	poly2->next; 	while (q) { 		p->next	= (PolyNode*)malloc(sizeof(PolyNode)); 		p =	p->next; 		p->coef	= -(q->coef);  //系数取反 		p->expn	= q->expn; 		q =	q->next; 	} 	p->next	= NULL; 	add(poly, poly1);  //利用加法 	return poly; } Polynomial polyAdd(Polynomial poly1, Polynomial	poly2) { //多项式相加 poly1+poly2形成一个新的多项式 	Polynomial poly	= (PolyNode*)malloc(sizeof(PolyNode));	//和多项式的头节点 	poly->next = NULL; 	PolyNode *p, *q, *r; 	r =	poly; 	p =	poly1->next; 	q =	poly2->next; 	while (p&&q) { 		if (p->expn	> q->expn) { 			r->next	= (PolyNode*)malloc(sizeof(PolyNode)); 			r =	r->next; 			r->coef	= p->coef; 			r->expn	= p->expn; 			p =	p->next; 		} else if (p->expn < q->expn) { 			r->next	= (PolyNode*)malloc(sizeof(PolyNode)); 			r =	r->next; 			r->coef	= q->coef; 			r->expn	= q->expn; 			q =	q->next; 		} else { 			float m	= p->coef +	q->coef; 			if (!(m	> -0.000001	&& m < 0.000001)) { 				r->next	= (PolyNode*)malloc(sizeof(PolyNode)); 				r =	r->next; 				r->coef	= m; 				r->expn	= p->expn; 			} 			q =	q->next; 			p =	p->next; 		} 	} 	while (p) { 		r->next	= (PolyNode*)malloc(sizeof(PolyNode)); 		r =	r->next; 		r->coef	= p->coef; 		r->expn	= p->expn; 		p =	p->next; 	} 	while (q) { 		r->next	= (PolyNode*)malloc(sizeof(PolyNode)); 		r =	r->next; 		r->coef	= q->coef; 		r->expn	= q->expn; 		q =	q->next; 	} 	r->next	= NULL; 	return poly; } Polynomial polyMultiply(Polynomial poly1, Polynomial poly2)	{  //多项式相乘 	Polynomial poly	= (PolyNode*)malloc(sizeof(PolyNode));	//创建多项式和的头节点 	poly->next = NULL; 	PolyNode *p; 	p =	poly2->next; 	while (p) { 		add(poly, multiply(poly1, p->coef, p->expn)); 		p =	p->next; 	} 	return poly; } void printPoly(Polynomial poly)	{  //打印多项式 	if (poly &&	poly->next)	{ 		PolyNode *p	= poly->next;  //p指向第一个节点 		while (p->next)	{ 			printf("%gx^%d", p->coef, p->expn); 			p =	p->next; 			if (p && (p->coef >	0)) 				printf("+"); 		} 		if (p->expn	== 0) 			printf("%g", p->coef);   //打印常数项 		else 			printf("%gx^%d", p->coef, p->expn); 		printf("\n"); 	} } void freePoly(Polynomial poly) {  //释放内存 	if (poly &&	poly->next)	{ 		PolyNode *p, *q; 		p =	poly; 		while (p) { 			q =	p->next; 			free(p); 			p =	q; 		} 	} 	poly = NULL; } int	main() { 	printf("用链表实现多项式的加减法\n"); 	Polynomial poly1, poly2, poly3; 	printf("创建多项式一\n"); 	poly1 =	createPolynomial(); 	printf("多项式一：\n"); 	printPoly(poly1); 	printf("创建多项式二\n"); 	poly2 =	createPolynomial(); 	printf("多项式二：\n"); 	printPoly(poly2); 	printf("两多项式相加，和为：\n"); 	poly3 =	polyAdd(poly1, poly2); 	printPoly(poly3); 	freePoly(poly3); 	printf("两个多项式相乘，积为：\n"); 	poly3 =	polyMultiply(poly1,	poly2); 	printPoly(poly3); 	freePoly(poly3); 	printf("两多项式相减，差为：\n"); 	poly3 =	polySubtract(poly1,	poly2); 	printPoly(poly3); 	freePoly(poly1); 	freePoly(poly2); 	freePoly(poly3); 	system("pause"); 	return 0; }

引用 1 楼 user-3的回复:这贴的图片，可能很难一下就看出哪里的问题阿。。。 可以请你帮我看看为什么printf（“”%c“”,a[i].data）输出不了吗 #include<stdio.h> #include<stdlib.h> #include<string.h> #define MAX_SIZE 1024 typedef struct{ char data; int weight; int parent; int lchild; int rchild; }Huffnode,*Hufftree; typedef struct stack{ int top; int elem[MAX_SIZE]; }Stack; void Initstack(Stack *s) { s->top=-1; } void push(Stack *s,int e) { s->top++; s->elem[s->top]=e; } int pop(Stack *s) { return s->elem[s->top--]; } bool isempty(Stack *s) { if(s->top==-1) return true; else return false; } void GetHuffmamCode(Hufftree a,int n) { int i,j,s1,s2,max,c,p; Stack s; char ch; Initstack(&s); printf("输入字符集："); for(i=1;i<=n;i++) { scanf("%c",&a[i].data); scanf("%c",&ch); } printf("输入权值："); for(i=1;i<=n;i++) { scanf("%d",&a[i].weight); scanf("%c",&ch); } int m=2*n-1; for(i=1;i<=n;i++) { a[i].parent=0; a[i].rchild=0; a[i].lchild=0; } for(i=n+1;i<=m;i++) { a[i].data=NULL; a[i].weight=0; a[i].parent=0; a[i].lchild=0; a[i].rchild=0; } for(i=n+1;i<=m;i++) { max=65535; for(j=1;j<=i-1;j++) { if(a[j].parent==0&&a[j].weight<=max) { s1=j; max=a[j].weight; } } a[s1].parent=i; max=65535; for(j=1;j<=i-1;j++) { if(a[j].parent==0&&a[j].weight<=max) { s2=j; max=a[j].weight; } } a[s2].parent=i; a[i].weight=a[s1].weight+a[s2].weight; a[i].lchild=s1; a[i].rchild=s2; } for(i=1;i<=n;i++) { c=i; p=a[i].parent; while(p!=0) { if(a[p].lchild==c) push(&s,0); else push(&s,1); c=p; p=a[p].parent; } printf("%c\n",a[i].data); while(!isempty(&s)) printf("%d",pop(&s)); printf("\n"); } } int main() { Hufftree a; int n; int m; printf("输入字符个数："); scanf("%d",&n); m=2*n-1; a=(Hufftree)malloc(sizeof(Huffnode)*m); GetHuffmamCode(a,n); return 0; }

#include<stdio.h> #include<stdlib.h> #include<malloc.h>    typedef struct polynode {     int coef;     int exp;     struct polynode *next; }polynode, *polylist;  polylist poly_create(void) {     polynode *rear, *head, *s;      int c, e;      rear = head = (polynode *)malloc(sizeof(polynode));     scanf("%d%d", &c, &e);      while (c) {         s = (polynode*)malloc(sizeof(polynode));         s->coef = c;         s->exp = e;         rear->next = s;         rear = s;         scanf("%d%d", &c, &e);     }     rear->next=NULL;      return(head); }    static void insert_node(polylist phead, polylist new_node) {     polylist pcur, pprev;      pprev = phead;     pcur = phead->next;      while (pcur && pcur->exp != new_node->exp) {         pprev = pcur;         pcur = pcur->next;     }     if (!pcur) {         pprev->next = new_node;         return;     }      pcur->coef += new_node->coef;     free(new_node);     if (pcur->coef == 0) {         pprev->next = pcur->next;         free(pcur);     } }  polylist multyploy(polylist pa, polylist pb) {     polylist pa_node, pb_node, pc_node, pc;     int coef, exp;       pc = (polynode*)malloc(sizeof(polynode));     if (!pc)         return NULL;      pa_node = pa->next;     pb_node = pb->next;      if (!pa_node || !pb_node) {         pc = pa_node ? pa : pb;     }     while (pa_node) {         while (pb_node) {             coef = pa_node->coef * pb_node->coef;             exp = pa_node->exp + pb_node->exp;              pc_node = (polylist)malloc(sizeof(polynode));             if (!pc_node)                 exit(0);             pc_node->coef = coef;             pc_node->exp = exp;             pc_node->next = NULL;              insert_node(pc, pc_node);             pb_node = pb_node->next;         }         pa_node = pa_node->next;         pb_node = pb->next;     }      return pc; }  void free_polylist(polylist phead) {     polylist pdel, pcur;      pcur = phead;      while (pcur) {         pdel = pcur;         pcur = pcur->next;         free(pdel);     } }  static void show_polylist(polylist phead) {     if (!phead)         return;      polylist pcur = phead->next;      while(pcur) {         printf("%d", pcur->coef);         printf("*x^%d", pcur->exp);         if (pcur->next)             printf(" + ");         pcur = pcur->next;     }     printf("\n"); }  int main(void) {     polylist pa, pb, pc;      pa = poly_create();     //show_polylist(pa);     pb = poly_create();     //show_polylist(pb);     pc = multyploy(pa, pb);      show_polylist(pc);      free_polylist(pa);     pa = NULL;     free_polylist(pb);     pb = NULL;     free_polylist(pc);     pc = NULL;      return 0; } 供参考～

引用 6 楼 user-3的回复:[quote=引用 5 楼 qq_51281859 的回复:] 我上面的代码是，分别给pa，pb链表赋值，幂从小到大，当赋值到因子为零时，结束循环，然后以第一个多项式的第一项和第二个多项式的每一项相乘，构造一个新的链表，然后以第一个多项式的第二项和第二个多项式的每一项相乘，查找第一个大于或等于这个幂的在链表中的位置，如果幂相等，则因数相加，相加如果等于零，则释放掉这个空间，如果查找到的大于这个幂，则将其插入，最后输出，可是我这构造的第一项与每一项相乘的新链表，单独的话可以输出，进行下面插入操作以后就不能输出了，不知道问题出现在哪里。  我的代码和你的基本也差不多，唯一的一点时， 在计算时， 没有处理coef==0 的情况， 问题是， 当计算某个项coef为0时， 后面的多项式又可能会出现这个项， 所以建议最后计算完后才处理coef==0 的式子， 另外一点，在生成 c 多项式时， 最好以插入排序的方式， 根据幂的大小， 由高到低排列， 这样多项式打印时，比较符合习惯。 [/quote] 我这个输入时按从小到大输入会比较方便，就是不懂为什么最后输出不了

引用 5 楼 qq_51281859 的回复:我上面的代码是，分别给pa，pb链表赋值，幂从小到大，当赋值到因子为零时，结束循环，然后以第一个多项式的第一项和第二个多项式的每一项相乘，构造一个新的链表，然后以第一个多项式的第二项和第二个多项式的每一项相乘，查找第一个大于或等于这个幂的在链表中的位置，如果幂相等，则因数相加，相加如果等于零，则释放掉这个空间，如果查找到的大于这个幂，则将其插入，最后输出，可是我这构造的第一项与每一项相乘的新链表，单独的话可以输出，进行下面插入操作以后就不能输出了，不知道问题出现在哪里。  我的代码和你的基本也差不多，唯一的一点时， 在计算时， 没有处理coef==0 的情况， 问题是， 当计算某个项coef为0时， 后面的多项式又可能会出现这个项， 所以建议最后计算完后才处理coef==0 的式子， 另外一点，在生成 c 多项式时， 最好以插入排序的方式， 根据幂的大小， 由高到低排列， 这样多项式打印时，比较符合习惯。

引用 4 楼 user-3的回复:试了一下上面的代码， 貌似出现无限循环的情况， 实在有点看不懂上面的代码，  下面改写了一个，还请指正   /**  * 在多项式中查找是否有幂为exp的项，  * 如有，返回指向Polynode指针  * 否则返回NULL  */ Polynode* searchByExp(Polylist p, int exp) { 	Polynode* x = p->next; 	while(x!=NULL) { 		if(x->exp == exp) { 			return x; 		} 		x = x->next; 	} 	return NULL; }  Polylist multyploy2(Polylist pa, Polylist pb) { 	Polynode *t1,*t2, *t3, *rear,*p;  	t1=pa->next; 	t2=pb->next;  	rear=p=(Polynode*)malloc(sizeof(Polynode)); 	p->next = NULL;  	while(t1!=NULL) { 		t2 = pb->next; 		while(t2!=NULL) { 			t3 = searchByExp(p, t1->exp+t2->exp ); 			if(t3==NULL) { 				// 生成新的项加入到p 				t3=(Polynode*)malloc(sizeof(Polynode)); 				t3->coef=t1->coef*t2->coef; 				t3->exp = t1->exp + t2->exp; 				t3->next=NULL; 				rear->next=t3; 				rear=t3; 			} 			else { 				t3->coef += (t1->coef*t2->coef); 			} 			t2=t2->next; 		}  		t1 = t1->next; 	}  	return p; }  我上面的代码是，分别给pa，pb链表赋值，幂从小到大，当赋值到因子为零时，结束循环，然后以第一个多项式的第一项和第二个多项式的每一项相乘，构造一个新的链表，然后以第一个多项式的第二项和第二个多项式的每一项相乘，查找第一个大于或等于这个幂的在链表中的位置，如果幂相等，则因数相加，相加如果等于零，则释放掉这个空间，如果查找到的大于这个幂，则将其插入，最后输出，可是我这构造的第一项与每一项相乘的新链表，单独的话可以输出，进行下面插入操作以后就不能输出了，不知道问题出现在哪里。

引用 8 楼 user-3的回复:不管是从大到小， 还是从小到大， 都可以， 其实要处理coef =0 的情况还是有些麻烦的， 比如 一个多项式， p=0x,  需要化简为 p=0,  还是 p=空  关于你的代码，貌似没有必要对第一次循环做特殊处理， 只用2层while 就可以了把, 伪代码是：  while each 式子 of  A {     while each  式子 of B  {          计算 A[i] * B[j] ,                加入到 C 中     } }  while each 式子 of C {      处理coef ==0  } 已经解决了，我又重新写了一个

引用 8 楼 user-3的回复:不管是从大到小， 还是从小到大， 都可以， 其实要处理coef =0 的情况还是有些麻烦的， 比如 一个多项式， p=0x,  需要化简为 p=0,  还是 p=空  关于你的代码，貌似没有必要对第一次循环做特殊处理， 只用2层while 就可以了把, 伪代码是：  while each 式子 of  A {     while each  式子 of B  {          计算 A[i] * B[j] ,                加入到 C 中     } }  while each 式子 of C {      处理coef ==0  } 我把中间相乘的函数改了一下，改成先把相乘结果各项存入链表，然后再同类项相加，可是还是无法输出，如果知道为什么无法输出，问题就解决了 Polylist multyploy(Polylist pa, Polylist pb) { 	Polynode *t1,*t2,*t3,*t,*rear,*p,*r; 	int c, e; 	t1=pa->next; 	p=(Polynode*)malloc(sizeof(Polynode)); 	rear=p; 	while(t1) 	{ 		t2=pb->next; 		while(t2) 		{ 			t=(Polynode*)malloc(sizeof(Polynode)); 			t->coef=t1->coef*t2->coef; 			t->exp=t1->exp+t2->exp; 			t->next=NULL; 			rear->next=t; 			rear=t; 			t2=t2->next; 		} 		t1=t1->next; 	} 	r=p->next; 	while(r->next) 	{ 		t3=r->next; 		while(t3&&t3->exp!=r->exp) 			t3=t3->next; 		if(t3==NULL) 			continue; 		else 		{ 			r->coef=r->coef+t3->coef; 			t=t3->next; 			t3->next=t->next; 			free(t); 		} 		r=r->next; 	} 	 	return (p); }

引用 1 楼 user-3的回复:这贴的图片，可能很难一下就看出哪里的问题阿。。。 大佬想要啥样的，我实在找不出来问题在哪了

引用 1 楼 user-3的回复:这贴的图片，可能很难一下就看出哪里的问题阿。。。 #include<stdio.h> #include<stdlib.h> #include<malloc.h> #define NULL 0 typedef struct Polynode { 	int coef;  //因子 	int exp;   //幂 	struct Polynode *next; }Polynode , * Polylist;  Polylist polycreate( )  { 	Polynode *rear, *head, *s; 	 	int c, e; 	 	rear=head=(Polynode *)malloc(sizeof(Polynode));   	scanf("%d%d",&c,&e);  	while(c!=0)  	{ 	 		s=(Polynode*)malloc(sizeof(Polynode)); 		s->coef=c;  		s->exp=e;  		rear->next=s;  		rear=s;   		scanf("%d%d",&c,&e);  	} 	rear->next=NULL;  	return(head); } Polylist multyploy(Polylist pa, Polylist pb) { 	Polynode *t1,*t2,*t3,*t,*rear,*p; 	int c, e; 	t1=pa->next; 	t2=pb->next; 	rear=p=(Polynode*)malloc(sizeof(Polynode)); 	while(t2) 	{ 		t3=(Polynode*)malloc(sizeof(Polynode)); 		t3->coef=t1->coef*t2->coef; 		t3->exp=t1->exp+t2->exp; 		t3->next=NULL; 		rear->next=t3; 		rear=t3; 		t2=t2->next; 	} 	t1=t1->next; 	while(t1) 	{ 		t2=pb->next; 		rear=p; 		while(t2) 		{ 			e=t1->exp+t2->exp; 			c=t1->coef*t2->coef; 			while(rear->next&&rear->next->exp<e) 				rear=rear->next; 			if(rear->next&&rear->next->exp==e) 			{ 				if(rear->next->coef+c) 					rear->next->coef+=c; 				else 				{ 					t=rear->next; 					rear->next=t->next; 					free(t); 					 				} 			} 			else 			{ 				t=(Polynode*)malloc(sizeof(Polynode)); 				t->coef=c; 				t->exp=e; 				t->next=rear->next; 				rear->next=t; 				rear=rear->next; 			} 		} 		t1=t1->next; 	} 	return (p); } void print(Polylist p) { 	p = p->next; 	while(p) 	{ 		printf("%d", p->coef); 		printf("*x^%d",p->exp); 		if(p->next!=NULL) 			printf(" + "); 		p = p->next; 	} 	printf("\n"); }  void main(int argc, char* argv[]) { 	Polylist pa, pb,pc;   //定义三个表示多项式的链表 	 	pa = polycreate();  //创建pa链表 	pb = polycreate();  //创建pb链表 	pc = multyploy(pa, pb);   //做乘法法，结果保存在pc链表上 	print(pc);      //将加法的结果用一个多项式格式显示在输出设备上 }

这贴的图片，可能很难一下就看出哪里的问题阿。。。


Question: 这个冒泡排序到底哪里出错？

引用 1 楼 user-2的回复:你这哪是排序？ ii在循环中一直不变，a[j]一直和ii固定位置的元素a[ii]比较 感谢，我之前以为ii会一直等于i+1，听你回复懂了

引用 2 楼 focuslight的回复:你那个 int a[i] 怎么没报错啊。 用常量声明数组啊 C99好像可以这样，不用malloc

你那个 int a[i] 怎么没报错啊。 用常量声明数组啊


Question: c语言

对于实数的比较，一般写法 #define EPS 1e-7 .....  while(fabs(a)-20>=EPS);

浮点数的比较不能像整形数那样比较.  https://blog.csdn.net/jk110333/article/details/8902707  供参考～

谢谢！

浮点数的精度原因致使浮点数不一定能准确存储表达一个数，所以不能用这种方式来比较， 可以用 a-20<一个精度范围 这样的方式来代替


Question: 这个代码没错吧，链表后面结点的值显示不出来？求大神帮忙

引用 3 楼 编程且快乐的回复:这个是我帮你修改的代码（如果觉得可以请结题一下）： struct list *getlink(int b[], int b1) { 	struct list *s,*h; 	struct list *head = NULL; 	int i; 	for ( i = b1-1; i>=0; i--) 	{ 		h = (struct list *)malloc(sizeof(struct list));	 		h->data = b[i]; 		h->next = NULL; 		if (head == NULL){ 			head = h; 		} 		else 		{ 			s->next = h; 		} 		s = h; 	} 	return head; } 多谢帮忙，改过来了

引用 1 楼 user-2的回复:if(h=NULL)  //错误在这一句，改成 if(h == NULL) 就正确了，条件判断写成赋值啦 h=s; 谢谢了，就错在赋值号上

你这个代码在读取数据的时候错了，这个链表函数struct list* getlink(int b[],int b1);错误，重新写一个就好了，你这个函数只读了一个数据进去，因为你的链表指向不对


Question: 为什么我这个最后输出不出来啊，有人帮忙看下吗？

#include<stdio.h> #include<stdlib.h> #include<malloc.h>    typedef struct polynode {     int coef;     int exp;     struct polynode *next; }polynode, *polylist;  polylist poly_create(void) {     polynode *rear, *head, *s;      int c, e;      rear = head = (polynode *)malloc(sizeof(polynode));     scanf("%d%d", &c, &e);      while (c) {         s = (polynode*)malloc(sizeof(polynode));         s->coef = c;         s->exp = e;         rear->next = s;         rear = s;         scanf("%d%d", &c, &e);     }     rear->next=NULL;      return(head); }    static void insert_node(polylist phead, polylist new_node) {     polylist pcur, pprev;      pprev = phead;     pcur = phead->next;      while (pcur && pcur->exp != new_node->exp) {         pprev = pcur;         pcur = pcur->next;     }     if (!pcur) {         pprev->next = new_node;         return;     }      pcur->coef += new_node->coef;     free(new_node);     if (pcur->coef == 0) {         pprev->next = pcur->next;         free(pcur);     } }  polylist multyploy(polylist pa, polylist pb) {     polylist pa_node, pb_node, pc_node, pc;     int coef, exp;       pc = (polynode*)malloc(sizeof(polynode));     if (!pc)         return NULL;      pa_node = pa->next;     pb_node = pb->next;      if (!pa_node || !pb_node) {         pc = pa_node ? pa : pb;     }     while (pa_node) {         while (pb_node) {             coef = pa_node->coef * pb_node->coef;             exp = pa_node->exp + pb_node->exp;              pc_node = (polylist)malloc(sizeof(polynode));             if (!pc_node)                 exit(0);             pc_node->coef = coef;             pc_node->exp = exp;             pc_node->next = NULL;              insert_node(pc, pc_node);             pb_node = pb_node->next;         }         pa_node = pa_node->next;         pb_node = pb->next;     }      return pc; }  void free_polylist(polylist phead) {     polylist pdel, pcur;      pcur = phead;      while (pcur) {         pdel = pcur;         pcur = pcur->next;         free(pdel);     } }  static void show_polylist(polylist phead) {     if (!phead)         return;      polylist pcur = phead->next;      while(pcur) {         printf("%d", pcur->coef);         printf("*x^%d", pcur->exp);         if (pcur->next)             printf(" + ");         pcur = pcur->next;     }     printf("\n"); }  int main(void) {     polylist pa, pb, pc;      pa = poly_create();     //show_polylist(pa);     pb = poly_create();     //show_polylist(pb);     pc = multyploy(pa, pb);      show_polylist(pc);      free_polylist(pa);     pa = NULL;     free_polylist(pb);     pb = NULL;     free_polylist(pc);     pc = NULL;      return 0; } 供参考～

算法太复杂了，刚好有时间，重新实现了一遍。大抵如下：   #include<stdio.h> #include<stdlib.h> #include<malloc.h>  typedef struct Polynode {     int coef;  //因子     int exp;   //幂     struct Polynode *next; } Polynode , *Polylist;  Polylist polycreate( ) {     Polynode *rear, *head, *s;     int c, e;      head = NULL;     rear = NULL;      while (1) {         scanf("%d%d",&c,&e);         if (c == 0)             break;          s = (Polynode *) malloc(sizeof(Polynode));         s->coef = c;         s->exp = e;         s->next = NULL;          if (head == NULL)             head = s;          if (rear != NULL) {             rear->next = s;         }         rear = s;     };      return head; }  Polylist multyploy(Polylist pa, Polylist pb) {     Polynode *n, *n1, *n2, *rslt, *rslt_rear, *new_item;     int coef, exp;      rslt = NULL;     rslt_rear = NULL;      for (n1 = pa; n1 != NULL; n1 = n1->next) {         for (n2 = pb; n2 != NULL; n2 = n2->next) {             coef = n1->coef*n2->coef;             exp = n1->exp + n2->exp;              // Find the right item to add the new result             for (n = rslt; n != NULL; n = n->next) {                 if (n->exp == exp)                     break;                 if (n->exp < exp && n->next != NULL && n->next->exp > exp)                     break;             }              // if item with identified exponent exists in result, just update its coefficient             if (n != NULL && n->exp == exp) {                 n->coef += coef;                 continue;             }              // new item needed             new_item = (Polynode *) malloc(sizeof(Polynode));             new_item->coef = coef;             new_item->exp = exp;             new_item->next = NULL;              // insert the new item, note sort if performed incrementally             if (n == NULL) {                 if (rslt == NULL) {                     rslt = new_item;                     rslt_rear = rslt;                 } else {                     rslt_rear->next = new_item;                     rslt_rear = new_item;                 }             } else {                 new_item->next = n->next;                 n->next = new_item;             }         } // iterate over the second polynominal     } // iterate over the first polynominal      return rslt; }  void print(Polylist p) {     while(p)     {         printf("%d", p->coef);         printf("*x^%d",p->exp);         if(p->next!=NULL)             printf(" + ");         p = p->next;     }     printf("\n"); }  void free_poly_list(Polylist head) {     Polynode *n0, *n1;     for (n0 = head; n0 != NULL; n0 = n1) {        n1 = n0->next;        free(n0);     } }  int main(int argc, const char* argv[]) {     Polylist pa, pb,pc;       //定义三个表示多项式的链表      pa = polycreate();        //创建pa链表     pb = polycreate();        //创建pb链表     pc = multyploy(pa, pb);   //做乘法法，结果保存在pc链表上     print(pc);      free_poly_list(pa);     free_poly_list(pb);     free_poly_list(pc);      return 0; }


Question: 为什么我这个最后输出不出来啊，有大神帮忙看下吗？

#include<stdio.h> #include<stdlib.h> #include<malloc.h>  //#define NULL 0 //#define NULL ((void *)0)  typedef struct Polynode {     int coef;  //因子     int exp;   //幂     struct Polynode *next; }Polynode , *Polylist;  Polylist polycreate( ) {     Polynode *rear, *head, *s;      int c, e;      rear=head=(Polynode *)malloc(sizeof(Polynode));     scanf("%d%d", &c, &e);      while(c) {         s = (Polynode*)malloc(sizeof(Polynode));         s->coef=c;         s->exp=e;         rear->next=s;         rear=s;         scanf("%d%d",&c,&e);     }     rear->next=NULL;      return(head); }    static void insert_node(Polylist phead, Polylist new_node) {     Polylist pcur, pprev;      pprev = phead;     pcur = phead->next;      while (pcur && pcur->exp != new_node->exp) {         pprev = pcur;         pcur = pcur->next;     }     if (!pcur) {         pprev->next = new_node;         return;     }      pcur->coef += new_node->coef;     free(new_node);     if (pcur->coef == 0) {         pprev->next = pcur->next;         free(pcur);     } }  Polylist multyploy(Polylist pa, Polylist pb) {     Polylist pa_node, pb_node, pc_node, pc;     int coef, exp;       pc = (Polynode*)malloc(sizeof(Polynode));     if (!pc)         return NULL;      pa_node = pa->next;     pb_node = pb->next;     while (pa_node) {          while (pb_node) {             coef = pa_node->coef * pb_node->coef;             exp = pa_node->exp + pb_node->exp;              pc_node = (Polylist)malloc(sizeof(Polynode));             if (!pc_node)                 exit(0);             pc_node->coef = coef;             pc_node->exp = exp;             pc_node->next = NULL;              insert_node(pc, pc_node);             pb_node = pb_node->next;         }         pa_node = pa_node->next;         pb_node = pb->next;    //保证pa的节点和pb的每个节点相乘     }      return pc; #if 0     Polynode *t1,*t2,*t3,*t,*rear,*p;     int c, e;     t1=pa->next;     t2=pb->next;     p=(Polynode*)malloc(sizeof(Polynode));     p->next=NULL;     rear=p;     while(t2)     {         t3=(Polynode*)malloc(sizeof(Polynode));         t3->coef=t1->coef*t2->coef;         t3->exp=t1->exp+t2->exp;         t3->next=NULL;         rear->next=t3;         rear=t3;         t2=t2->next;     }     t1=t1->next;     while(t1)     {         t2=pb->next;         rear=p;         while(t2)         {             e=t1->exp+t2->exp;             c=t1->coef*t2->coef;             while(rear->next&&rear->next->exp<e)                 rear=rear->next;             if(rear->next&&rear->next->exp==e)             {                 if(rear->next->coef+c)                     rear->next->coef+=c;                 else                 {                     t=rear->next;                     rear->next=t->next;                     free(t);                  }             }             else             {                 t=(Polynode*)malloc(sizeof(Polynode));                 t->coef=c;                 t->exp=e;                 t->next=rear->next;                 rear->next=t;                 rear=rear->next;             }         }         t1=t1->next;     }     t2=p;     p=p->next;     free(t2);     return p; #endif }  void print(Polylist p) {     p = p->next;     while(p)     {         printf("%d", p->coef);         printf("*x^%d",p->exp);         if(p->next!=NULL)             printf(" + ");         p = p->next;     }     printf("\n"); }  //void main(int argc, char* argv[]) int main(int argc, char* argv[]) {     Polylist pa, pb,pc;   //定义三个表示多项式的链表      pa = polycreate();  //创建pa链表     //print(pa);      //将加法的结果用一个多项式格式显示在输出设备上     pb = polycreate();  //创建pb链表     //print(pb);      //将加法的结果用一个多项式格式显示在输出设备上     pc = multyploy(pa, pb);   //做乘法法，结果保存在pc链表上     print(pc);      //将加法的结果用一个多项式格式显示在输出设备上 } 供参考～

纯粹是为了这50分  算法太复杂了，刚好有时间，重新实现了一遍。大抵如下：   #include<stdio.h> #include<stdlib.h> #include<malloc.h>  typedef struct Polynode {     int coef;  //因子     int exp;   //幂     struct Polynode *next; } Polynode , *Polylist;  Polylist polycreate( ) {     Polynode *rear, *head, *s;     int c, e;      head = NULL;     rear = NULL;      while (1) {         scanf("%d%d",&c,&e);         if (c == 0)             break;          s = (Polynode *) malloc(sizeof(Polynode));         s->coef = c;         s->exp = e;         s->next = NULL;          if (head == NULL)             head = s;          if (rear != NULL) {             rear->next = s;         }         rear = s;     };      return head; }  Polylist multyploy(Polylist pa, Polylist pb) {     Polynode *n, *n1, *n2, *rslt, *rslt_rear, *new_item;     int coef, exp;      rslt = NULL;     rslt_rear = NULL;      for (n1 = pa; n1 != NULL; n1 = n1->next) {         for (n2 = pb; n2 != NULL; n2 = n2->next) {             coef = n1->coef*n2->coef;             exp = n1->exp + n2->exp;              // Find the right item to add the new result             for (n = rslt; n != NULL; n = n->next) {                 if (n->exp == exp)                     break;                 if (n->exp < exp && n->next != NULL && n->next->exp > exp)                     break;             }              // if item with identified exponent exists in result, just update its coefficient             if (n != NULL && n->exp == exp) {                 n->coef += coef;                 continue;             }              // new item needed             new_item = (Polynode *) malloc(sizeof(Polynode));             new_item->coef = coef;             new_item->exp = exp;             new_item->next = NULL;              // insert the new item, note sort if performed incrementally             if (n == NULL) {                 if (rslt == NULL) {                     rslt = new_item;                     rslt_rear = rslt;                 } else {                     rslt_rear->next = new_item;                     rslt_rear = new_item;                 }             } else {                 new_item->next = n->next;                 n->next = new_item;             }         } // iterate over the second polynominal     } // iterate over the first polynominal      return rslt; }  void print(Polylist p) {     while(p)     {         printf("%d", p->coef);         printf("*x^%d",p->exp);         if(p->next!=NULL)             printf(" + ");         p = p->next;     }     printf("\n"); }  void free_poly_list(Polylist head) {     Polynode *n0, *n1;     for (n0 = head; n0 != NULL; n0 = n1) {        n1 = n0->next;        free(n0);     } }  int main(int argc, const char* argv[]) {     Polylist pa, pb,pc;       //定义三个表示多项式的链表      pa = polycreate();        //创建pa链表     pb = polycreate();        //创建pb链表     pc = multyploy(pa, pb);   //做乘法法，结果保存在pc链表上     print(pc);      free_poly_list(pa);     free_poly_list(pb);     free_poly_list(pc);      return 0; }


Question: 求助free()问题

懂了，谢谢。

问题就在于删除的节点不是自己申请的内存，是指向main函数的z变量，z是不能free的（因为z的内存是程序自动分配的，不是自己申请的），只有自己malloc申请的内存才需要free。


Question: 求问前辈们一道问题 B: 栈的操作问题

引用 1 楼 user-1的回复:其实就是看你对栈的入栈出栈顺利的理解和把握。说白了就是比较输入的数据和栈顶的数据，根据比较结果来打印入栈出栈指令。如果输入数据和栈顶一致，就把栈顶出栈（并打印Q）；如果输入数据大于栈顶元素，就把元素一次入栈（并打印P，这里要注意没有重复入栈，所以判断一下上次入栈的最大值，如果输入数据比上次入栈的最大值小，则说明重复入栈，出错）；如果输入数据小于栈顶数据则错误打印error（因为栈顶再怎么出栈打印，打印结果也和输入数据不相符，所以是错误的）  #define Maxsize 1000 typedef struct{     int data[Maxsize];     int top; }SqStack; void InitStack(SqStack &s){     s.top=-1; } void Push(SqStack &s,int x){     if(s.top==Maxsize-1) return;     s.data[++s.top]=x; } int Pop(SqStack &s){     if(s.top==-1){         return -1;     }     return s.data[s.top--]; } int Peek(SqStack &s) { //加个查看栈顶元素的方法     if (s.top==-1) {         return -1;     }     return s.data[s.top]; }  int main(){     int n, i, j, t, m; //n是每行第一个数，i是n的计数器，j是记录上一次入栈的最大值（以后入栈只能从最大值+1开始），t是栈顶数据，m是每行的输入数据     SqStack s;     char res[2*Maxsize+1]; //res是指令结果字符串     while (scanf("%d", &n)==1 && n>0) { //获取每行第一个数n（n是0或非法输入则结束测试）         memset(res, 0, sizeof(res)); //初始化res         InitStack(s); //初始化栈         for(i=1, j=0; i<=n; i++) { //n循环             scanf("%d", &m); //获取每行的每个数据m             if (strstr(res, "error") != NULL) { //如果结果已经出错就跳过该行剩余的输入数据                 continue;             }             t = Peek(s); //获得栈顶数据             if (t==m) { //如果输入数据和栈顶一致，则打印Q，并弹出栈顶元素                 strcat(res, "Q");                 Pop(s);             } else if (t<m) { //如果输入数据大于栈顶元素（栈顶为空也包含在里面）                 if (m<j+1) { //如果m小于上次入栈的最大值+1，则出错（因为已经入过栈了，不能重复入栈）                     strcat(res, " error");                 } else { //从上次入栈的                     for(t=j+1; t<m; ++t) { //从上次入栈的最大值+1开始依次入栈，并打印P                         strcat(res, "P");                         Push(s, t);                     }                     strcat(res, "PQ"); //最后一个入栈后又马上出栈了，所以直接打印PQ                     j = m; //记录入栈过的最大值                 }             } else { //如果输入数据小于栈顶元素（那栈顶出栈打印的结果就和输入数据不相符，所以错误）                 strcat(res, " error");             }         }         printf("%s\n", res); //最后打印指令结果     }     return 0; } 前辈能解释下为什么要用栈顶元素和输入数据比较吗？ 或者说该怎么思考到这种方法思路


Question: 有没有大神看看为什么最后只删除了一个7

#include<stdio.h> #include<stdlib.h> #define MAX 20 typedef struct{ 	int n; 	int data[MAX]; }SEQTABLE;  void delitem(SEQTABLE * st,int e) { 	int i,j; 	for(i=j=0;i<st->n;i++) 		if(st->data[i]!=e) 			st->data[j++]=st->data[i]; 	st->n=j; } int  main() { 	int i; 	SEQTABLE st = {10, {0,5,7,9,8,7,2,6,7,9}}; 	delitem(&st, 7); 	for(i =0; i < st.n; i++) 		printf("%4d", st.data[i]); 	printf("\n"); 	return 0; }

#include<stdio.h> #include<stdlib.h>  #define MAX 20  typedef struct{     int n;     int data[MAX+1]; } SEQTABLE;  void delitem(SEQTABLE * st,int e) {     int i, j;     for(i=1;i<=st->n;i++)     {         if(st->data[i]==e)         {             //for(i;i<st->n;i++)             for(j = i;j < st->n; j++)                 st->data[j] = st->data[j+1];             --st->n;             --i;         }     } } int  main() {     int i;      SEQTABLE st = {9, {0,5,7,9,8,7,2,6,7,9}};     delitem(&st, 7);     for(i = 1; i <= st.n; i++)     {         printf("%4d", st.data[i]);     }     printf("\n");     return 0; } 供参考～

引用 4 楼 focuslight的回复:void print(Polylist p) { p = p->next; while(p)   --------------  看看p是否为null P的null空间已经被释放掉了，我改了一下还是输出不出来

引用 1 楼 focuslight的回复:要这么写， 你里面的for循环把i走到st->n了， 外围的循环就只走到 第一个7那里就停了  #include<stdio.h> #include<stdlib.h> #define MAX 20 typedef struct{ int n; int data[MAX+1]; } SEQTABLE;  void delitem(SEQTABLE * st,int e) { int i, j; for(i=0;i<=st->n;i++) {     j=i; if(st->data[i]==e) {      for(j;j<st->n;j++) st->data[j]=st->data[j+1]; --st->n; --i; } } } int  main() { int i;  SEQTABLE st = {9, {0,5,7,9,8,7,2,6,7,9}}; delitem(&st, 7); for(i = 0; i <= st.n; i++) { printf("%4d", st.data[i]); } printf("\n"); return 0; }  谢谢谢谢，懂了

引用 1 楼 focuslight的回复:要这么写， 你里面的for循环把i走到st->n了， 外围的循环就只走到 第一个7那里就停了  #include<stdio.h> #include<stdlib.h> #define MAX 20 typedef struct{ int n; int data[MAX+1]; } SEQTABLE;  void delitem(SEQTABLE * st,int e) { int i, j; for(i=0;i<=st->n;i++) {     j=i; if(st->data[i]==e) {      for(j;j<st->n;j++) st->data[j]=st->data[j+1]; --st->n; --i; } } } int  main() { int i;  SEQTABLE st = {9, {0,5,7,9,8,7,2,6,7,9}}; delitem(&st, 7); for(i = 0; i <= st.n; i++) { printf("%4d", st.data[i]); } printf("\n"); return 0; }  可以再问你一个问题吗，我这个程序最后怎么输出不出来啊 #include<stdio.h> #include<stdlib.h> #include<malloc.h> #define NULL 0 typedef struct Polynode { int coef;  //因子 int exp;   //幂 struct Polynode *next; }Polynode , * Polylist;  Polylist polycreate( )  { Polynode *rear, *head, *s;  int c, e;  rear=head=(Polynode *)malloc(sizeof(Polynode));   scanf("%d%d",&c,&e);  while(c!=0)  {  s=(Polynode*)malloc(sizeof(Polynode)); s->coef=c;  s->exp=e;  rear->next=s;  rear=s;   scanf("%d%d",&c,&e);  } rear->next=NULL;  return(head); } Polylist multyploy(Polylist pa, Polylist pb) { Polynode *t1,*t2,*t3,*t,*rear,*p; int c, e; t1=pa->next; t2=pb->next; p=(Polynode*)malloc(sizeof(Polynode)); p->next=NULL; rear=p; while(t2) { t3=(Polynode*)malloc(sizeof(Polynode)); t3->coef=t1->coef*t2->coef; t3->exp=t1->exp+t2->exp; t3->next=NULL; rear->next=t3; rear=t3; t2=t2->next; } t1=t1->next; while(t1) { t2=pb->next; rear=p; while(t2) { e=t1->exp+t2->exp; c=t1->coef*t2->coef; while(rear->next&&rear->next->exp<e) rear=rear->next; if(rear->next&&rear->next->exp==e) { if(rear->next->coef+c) rear->next->coef+=c; else { t=rear->next; rear->next=t->next; free(t);  } } else { t=(Polynode*)malloc(sizeof(Polynode)); t->coef=c; t->exp=e; t->next=rear->next; rear->next=t; rear=rear->next; } } t1=t1->next; } t2=p; p=p->next; free(t2); return p; } void print(Polylist p) { p = p->next; while(p) { printf("%d", p->coef); printf("*x^%d",p->exp); if(p->next!=NULL) printf(" + "); p = p->next; } printf("\n"); }  void main(int argc, char* argv[]) { Polylist pa, pb,pc;   //定义三个表示多项式的链表  pa = polycreate();  //创建pa链表 pb = polycreate();  //创建pb链表 pc = multyploy(pa, pb);   //做乘法法，结果保存在pc链表上 print(pc);      //将加法的结果用一个多项式格式显示在输出设备上 }


Question: c语言为什么printf显示为定义标识符

printf( printf（ 不一样

对的。。。。

呵呵，用了中文括号了吧？

我明白了 printf后面那个括号格式不对


Question: 为什么将p=p->next 改为p++会报错？？

引用 9 楼 均陵鼠侠 的回复:感谢夸奖，哈哈！不过我还是中意我的《C语言非常道》，《标准C语言指南》太辞典化了。 个人感觉不同吧，没觉得《标准C语言指南》太辞典化，比原版标准好读多了 市面上只有你的《标准C语言指南》和Guy L. Steele Jr.的《C语言参考手册(原书第5版)》对原版标准有自己的诠释 有空再拜读你的《C语言非常道》

[quote=引用 9 楼 均陵鼠侠 的回复: 感谢夸奖，哈哈！不过我还是中意我的《C语言非常道》，《标准C语言指南》太辞典化了。[/quote] 个人感觉不同吧，没觉得《标准C语言指南》太辞典化，比原版标准好读多了 市面上只有你的《标准C语言指南》和Guy L. Steele Jr.的《C语言参考手册(原书第5版)》对原版标准有自己的诠释 有空再拜读你的《C语言非常道》，

引用 7 楼 Intel0011 的回复:[quote=引用 6 楼 均陵鼠侠 的回复:][quote=引用 5 楼 Intel0011 的回复:][quote=引用 4 楼 Intel0011 的回复:]简单来讲，就是p指向的是结构，是聚合，不是标量，所以p++非法，后缀运算符++要求操作数是标量 更正一下： 后缀运算符++要求操作数是实数类型或是指针类型 结构是聚合类型，所以p++非法 标量还包含了复数类型，而复数类型参与运算符++时，会自动进行实数-复数转换 [/quote]  指针类型是标量。请参照这幅图，确认你对标量的理解是正确的。另外，p是指针，p ++ 是没有问题的。 [/quote] 的确我看错了，p是指针，是标量 P.S.  均陵鼠侠，你的《标准C语言指南》非常赞 [/quote]  感谢夸奖，哈哈！不过我还是中意我的《C语言非常道》，《标准C语言指南》太辞典化了。

均陵鼠侠，你的《标准C语言指南》的勘误在哪里，你的网站上没发现

引用 6 楼 均陵鼠侠 的回复:[quote=引用 5 楼 Intel0011 的回复:][quote=引用 4 楼 Intel0011 的回复:]简单来讲，就是p指向的是结构，是聚合，不是标量，所以p++非法，后缀运算符++要求操作数是标量 更正一下： 后缀运算符++要求操作数是实数类型或是指针类型 结构是聚合类型，所以p++非法 标量还包含了复数类型，而复数类型参与运算符++时，会自动进行实数-复数转换 [/quote]  指针类型是标量。请参照这幅图，确认你对标量的理解是正确的。另外，p是指针，p ++ 是没有问题的。 [/quote] 的确我看错了，p是指针，是标量 P.S.  均陵鼠侠，你的《标准C语言指南》非常赞

引用 5 楼 Intel0011 的回复:[quote=引用 4 楼 Intel0011 的回复:]简单来讲，就是p指向的是结构，是聚合，不是标量，所以p++非法，后缀运算符++要求操作数是标量 更正一下： 后缀运算符++要求操作数是实数类型或是指针类型 结构是聚合类型，所以p++非法 标量还包含了复数类型，而复数类型参与运算符++时，会自动进行实数-复数转换 [/quote]  指针类型是标量。请参照这幅图，确认你对标量的理解是正确的。另外，p是指针，p ++ 是没有问题的。

引用 4 楼 Intel0011 的回复:简单来讲，就是p指向的是结构，是聚合，不是标量，所以p++非法，后缀运算符++要求操作数是标量 更正一下： 后缀运算符++要求操作数是实数类型或是指针类型 结构是聚合类型，所以p++非法 标量还包含了复数类型，而复数类型参与运算符++时，会自动进行实数-复数转换

谢邀。 其实代码不用全发出来，只发一点点就足够了。 首先，你要明白链表是怎么回事。想象一下，如果把struct student看成家庭，那么，指针变量p的值指向一个家庭 a，家庭的成员next知道另一个家庭 b。这样的话，如果变量p一开始指向家庭a，那么，p = p->next就使得变量p指向家庭 b。这里的关键是，家庭a和b可能不在一起，相距很远，位置不确定，但是它们可以通过家庭的成员next彼此建立关联。 再来看表达式 p ++。如果 p 的类型是 T，那么，p++等价于 p = p + sizeof (T)，或者说，p = p + sizeof p。就是说，在p原来的基础上，再加上p的大小，或者p的类型的大小。显然，p++的结果是指向p后面的内存位置。所以p ++ 要求所有“家庭”必须是连续的、紧邻的。

#define _CRT_SECURE_NO_WARNINGS #include<stdio.h> #define N 3 struct student { 	int num; 	char name[50]; 	char sex; 	int age; 	struct student* next; }; void input(struct student* stu) { 	struct student* p; 	int i=0; 	for (p = stu; p < stu + N; p++,i++) 	{ 		printf("第%d位:", i + 1); 		scanf("%d %s %c %d", &p->num, p->name, &p->sex, &p->age); 		i == N - 1 ? (stu[i].next = NULL) : (stu[i].next = &stu[i + 1]); 	} } void print(struct student *stu) { 	struct student *p; 	for (p = stu; p->next!=NULL; p=p->next); 	{ 		printf("%d %s %c %d", p->num, p->name, p->sex, p->age); 	} } struct student* del(struct student* stu,int n) { 	struct student* p,*head; 	for (p = stu,head=p; p != NULL;p=p->next) 	{ 		if (p->age == n) 		{ 			if (p == head) 			{ 				head = p->next; 			} 			else if (p->next == NULL) 			{ 				(p - 1)->next = NULL; 			} 			else 			{ 				(p - 1)->next = p + 1; 			} 		} 	} 	return head; } int main() { 	int n; 	struct student stu[3]; 	printf("请依次输入 学号 姓名 性别 年龄：\n"); 	input(stu); 	printf("请输入一个年龄：\n"); 	scanf("%d", &n); 	print(del(stu,n)); }

代码被挡了。。我重新发