跳转至

编程错题本

C 语言并查集易错点

1. 语法错

printf 要用双引号

  • 错:printf('yes');
  • 对:printf("yes\n");
  • 记法:单引号是字符,双引号才是字符串

union 不能当函数名

  • 错:void union(int S[], int a, int b)
  • 对:void UnionSet(int S[], int a, int b)
  • 记法:union 是 C 语言关键字

数组传参不要乱写 []

  • 错:
  • void Initial(S[], int n)
  • Initial(S[], n)
  • 对:
  • void Initial(int S[], int n)
  • Initial(S, n)
  • 记法:定义时要写类型,调用时只写数组名

2. 输入输出错

scanf("%c") 容易读到回车

  • 错:scanf("%c", &op)
  • 对:scanf(" %c", &op)
  • 记法:%c 前面加空格,先吃掉空白字符

scanf 的返回值不是读到的内容

  • 错:while (scanf(" %c", &op) != 'S')
  • 对:while (scanf(" %c", &op) != EOF && op != 'S')
  • 记法:
  • scanf(...) 比较的是有没有读成功
  • op 比较的才是读到了什么

3. 并查集逻辑错

Find 判断条件别写错

  • 错:for (root = x; root >= 0; root = S[root])
  • 也不稳:S[root] > 0
  • 对:for (root = x; S[root] >= 0; root = S[root]);
  • 记法:
  • S[i] < 0i 是根
  • S[i] >= 0i 还有父结点
  • 如果下标从 0 开始,写 > 0 会漏掉父结点刚好是 0 的情况

合并时比的是集合大小,不是根编号

  • 错:if (root1 > root2) ...
  • 对:if (S[root1] > S[root2]) ...
  • 记法:
  • 比较的是 S[root]
  • 根里存的是负数
  • 数值越大,集合越小

合并前一定先找根

  • 错:UnionSet(S, S[b], S[c]);
  • 对:UnionSet(S, Find(S, b), Find(S, c));
  • 记法:并查集的 Union 永远合并两个根