谷动谷力

 找回密码
 立即注册
查看: 1433|回复: 0
打印 上一主题 下一主题
收起左侧

C语言中的不完整类型

[复制链接]
跳转到指定楼层
楼主
发表于 2023-2-4 10:13:04 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
C语言中的不完整类型


C语言中存在这样一种类型,名叫不完整类型(Incomplete types),虽然我们可能不太理解,或许也没有仔细研究过,但是在实际的编程中,我们却已经用到过很多次了。

接下来,我们就来学习一下,内容比较简单,一看就懂,一学就会。



不完整类型

不完整类型(Incomplete types)是缺少足够信息来确定该类型对象大小的对象类型,不完整类型可以在翻译单元的某些点完整。

听起来可能比较绕口,简单来说就是,不完整类型是不知道对象所占空间大小,此时是无法使用sizeof()的。但是可以通过后续再补充完整。

不完整类型主要有下面三种。


已声明但未定义的类类型

内容未知的结构体或联合体类型。在同一作用域的后面,定义同一结构体或联合体的内容的声明能使之完整。

struct node {
  struct node *next; // struct node 在此点不完整
}; // struct node 在此点完整

未知边界数组

简单来说就是大小未知的数组,之后指定大小的声明能使之完整,接下来看一个示例。

#include<stdio.h>

extern int a[];  //此时a类型为int []是不完整类型

void fun1() {
  printf("sizeof a = %d\r\n", sizeof(a)); // error
  a[0] = 88;  //OK
}

int a[3] = {1,2,3};  //此时a类型为int [3]是完整类型

void fun2() {
  printf("sizeof a = %d\r\n", sizeof(a));  //OK
  a[0] = 3;  //OK
}

int main(int argc ,char **argv) {
  fun1();
  fun2();
  return 0;
}

如果在fun1函数中打印数组a的长度编译时就会报如下错误:

  1. invalid application of 'sizeof' to incomplete type 'int[]'
复制代码



因为此时a为不完整类型,即不知道a的长度,所以无法使用sizeof。

但有的小伙伴却有疑问了,为什么在fun1函数中却可以设置a[0]的值?

虽然这里使用了数组a,但是它会被转换成指向其首元素的指针,而且这个转换并不需要知道数组的大小。

而且C语言也不会检查数组是否越界,他选择相信程序员,把重心放在了程序的执行效率上,这也是为什么C语言执行效率高运行快的原因。

感兴趣的可以参考:为什么C语言执行效率高,运行快?

其实在外部声明的时候可以完整声明,例如上述示例我可以改为:extern int a[3];

此时在编译程序fun1就不会有编译报错提示了。

因为数组元素不能具有未知边界数组类型,所以多维数组只能在第一个维度中有未知边界:


  1. extern int a[][2]; // OK:边界未知的含有【2 个 int 元素的数组】元素的数组
  2. extern int b[2][]; // error:数组有不完整类型
复制代码

void 类型

可由 CV 限定,有别于其他不完整类型, void 不能补充声明为完整类型。


总结

不完整类型有三种:

  • void类型(不能被完整)
  • 数组长度未知(可被完整)
  • 已声明但未定义的类类型(可被完整)
参考链接
  • https://en.cppreference.com/w/c/language/type
  • https://en.cppreference.com/w/cpp/language/type


+10
回复

使用道具 举报

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

本版积分规则

QQ|Archiver|手机版|深圳市光明谷科技有限公司|光明谷商城|Sunshine Silicon Corpporation ( 粤ICP备14060730号|Sitemap

GMT+8, 2024-12-28 10:09 , Processed in 0.085680 second(s), 39 queries .

Powered by Discuz! X3.2 Licensed

© 2001-2013 Comsenz Inc.

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