@2019-07-31

  1. struct MyData
  2. {
  3. int nLen;
  4. char data[];
  5. };

开始没有理解红色部分的内容,上网搜索下,发现用处很大,记录下来。

在结构中,data是一个数组名;但该数组没有元素;该数组的真实地址紧随结构体MyData之后,而这个地址就是结构体后面数据的地址(如果给这个结构体分配的内容大于这个结构体实际大小,后面多余的部分就是这个data的内容);这种声明方法可以巧妙的实现C语言里的数组扩展。

实际用时采取这样:
  struct MyData *p = (struct MyData *)malloc(sizeof(struct MyData )+strlen(str)),这样就可以通过p->data 来操作这个str。

示例:

  1. #include <iostream>
  2.  
  3. using namespace std;
  4.  
  5. struct MyData
  6. {
  7. int nLen;
  8. char data[];
  9. };
  10.  
  11. int main()
  12. {
  13. int nLen = ;
  14. char str[] = "";
  15.  
  16. cout << "Size of MyData: " << sizeof(MyData) << endl;
  17.  
  18. MyData *myData = (MyData*)malloc(sizeof(MyData) + );
  19. memcpy(myData->data, str, );
  20.  
  21. cout << "myData's Data is: " << myData->data << endl;
  22.  
  23. free(myData);
  24.  
  25. return ;
  26. }

输出:

  Size of MyData: 4
  myData's Data is: 123456789        
由于数组没有元素,该数组在该结构体中分配占用空间,所以sizeof(struct Mydata) = 4。
malloc申请的是14个字节的连续空间,它返回一个指针指向这14个字节,强制转换成struct INFO的时候,前面4个字节被认为是Mydata结构,后面的部分拷贝了“123456789”的内容。

在读程序中经常会看到这样的定义char data[0],这是一个什么样的用法,有什么好处,在哪些地方用到?

本文的主要目的就是阐明这个定义的作用,以及适用范围,这需要对指针的概念和操作系统的内存模型有一个情形的认识。

首先看一段程序:

  1. #include <stdio.h>
  2.  
  3. #include <string.h>
  4.  
  5. #include <stdlib.h>
  6.  
  7. typedef struct _Info
  8.  
  9. {
  10.  
  11. int i;
  12.  
  13. char data[];
  14.  
  15. }Info;
  16.  
  17. int main(int argc, char* argv[])
  18.  
  19. {
  20.  
  21. printf("%d/n",sizeof(Info));
  22.  
  23. return ;
  24.  
  25. }

程序的执行结果是:4。

整数i就占了4个字节,这表明data没有占用空间。data是一个数组名;该数组没有元素;该数组的真实地址紧随结构体Info之后;这种声明方法可以巧妙的实现C语言里的数组扩展。

记住上面的结构体不同于:

  1. typedef struct _Info
  2.  
  3. {
  4.  
  5. int i;
  6.  
  7. char* data;
  8.  
  9. }Info;

这个结构体占用8个字节的空间,因为指针类型要占用4个字节的空间。

再看一个例子:

  1. #include <stdio.h>
  2.  
  3. #include <string.h>
  4.  
  5. #include <stdlib.h>
  6.  
  7. typedef struct _Info
  8. {
  9. int i;
  10.  
  11. char data[];
  12.  
  13. }Info;
  14.  
  15. int main(int argc, char* argv[])
  16. {
  17.  
  18. char buf[] = "";
  19.  
  20. void* p = NULL;
  21.  
  22. printf("%d\n",sizeof(Info));
  23.  
  24. Info* info = (Info*)malloc(sizeof(Info) + );
  25.  
  26. p = (void*)info->data;
  27.  
  28. printf("addr of info is %p. addr of data is %p ./n", info, p);
  29.  
  30. strcpy((char*)p, buf);
  31.  
  32. printf("%s\n", (char*)p);
  33.  
  34. return ;
  35. }

程序的执行结果:

  4
  addr of info is 0x188b020. addr of data is 0x188b024 .
  123456789

可知,data的地址是紧随结构体之后的。

来源

【转】char data[0]用法总结的更多相关文章

  1. C语言变长数组 struct中char data[0]的用法

    版权声明:本文为博主原创文章,未经博主允许不得转载. 今天在看一段代码时出现了用结构体实现变长数组的写法,一开始因为忘记了这种技术,所以老觉得作者的源码有误,最后经过我深思之后,终于想起以前看过的用s ...

  2. [C/C++] char data[0](柔性数组)

    转自:http://blog.csdn.net/yby4769250/article/details/7294696 在标准C和C++中0长数组如charArray[0]是不允许使用的,因为这从语义逻 ...

  3. 柔性数组 data[0]

    struct MyData {    int nLen;    char data[0];}; 在结构中,data是一个数组名:但该数组没有元素:该数组的真实地址紧随结构体MyData之后,而这个地址 ...

  4. C语言变长数组data[0]

    1.前言 在刷题时遇到一个结构中包含char data[0],第一次见到时感觉很奇怪,数组的长度怎么可以为零呢?于是上网搜索一下这样的用法的目的,发现在linux内核中,结构体中经常用到data[0] ...

  5. C语言变长数组data[0]【总结】

    1.前言 今天在看代码中遇到一个结构中包含char data[0],第一次见到时感觉很奇怪,数组的长度怎么可以为零呢?于是上网搜索一下这样的用法的目的,发现在linux内核中,结构体中经常用到data ...

  6. C语言变长数组data[0]总结

    C语言变长数组data[0] 1.前言 今天在看代码中遇到一个结构中包含char data[0],第一次见到时感觉很奇怪,数组的长度怎么可以为零呢?于是上网搜索一下这样的用法的目的,发现在linux内 ...

  7. C中char类型的用法

    代码 /* char类型的用法 */ #include <stdio.h> main(int argc, char *argv[]) { /* 声明字符变量c1 */ char c1 = ...

  8. Vue1.0用法详解

    Vue.js 不支持 IE8 及其以下版本,因为 Vue.js 使用了 IE8 不能实现的 ECMAScript 5 特性. 开发环境部署 可参考使用 vue+webpack. 基本用法 1 2 3 ...

  9. mysql导入数据load data infile用法

    mysql导入数据load data infile用法 基本语法: load data [low_priority] [local] infile 'file_name txt' [replace | ...

随机推荐

  1. pycharm建立第一个django工程-----windows中

    pycharm建立第一个django工程 系统:win764 ip: 192.168.0.100 安装django pip install django 左上角建立一个名为Firstdjango工程 ...

  2. 使用apache commons net进行ftp传输

    apache commons net的maven地址: http://mvnrepository.com/artifact/commons-net/commons-net/3.6 <!-- ht ...

  3. 神经网络(NN)实现多分类-----Keras实现

    IRIS数据集介绍   IRIS数据集(鸢尾花数据集),是一个经典的机器学习数据集,适合作为多分类问题的测试数据,它的下载地址为:http://archive.ics.uci.edu/ml/machi ...

  4. swift 第五课 定义model类 和 导航栏隐藏返回标题

    1. 网络请求返回数据时候,把数据转化为model,但是有时候会返回空的字符串,所以加载了个长度的判断: class Model : NSObject{ var details_url:String? ...

  5. 6种php加密解密方法

    <?php function encryptDecrypt($key, $string, $decrypt){ if($decrypt){ $decrypted = rtrim(mcrypt_d ...

  6. CImage 和 CvvImage 命名空间问题

    [问题:名称CImage同时在两个库中出现] 1.出现: ATL #include <atlimage.h> OpenCv #include <highgui.h> #defi ...

  7. C#实现隐藏手机号、邮箱、姓名等敏感信息扩展方法

    还是老惯例,直接上代码. 最终效果图: public static class HideSensitiveInfoExtension { /// <summary> /// 隐藏敏感信息 ...

  8. 鼠标拖拉div宽度

    先看效果 先进入页面 当鼠标停留在中间div时,鼠标变成双箭头 点击拖拉 往右边拉 往最左边拉 代码 <!DOCTYPE html> <html> <head> & ...

  9. 在C#中简单使用gRPC

    一.引言 本文采用gRPC官方提供的一个教程例子,通过这个例子可以学习到在.proto文件中定义服务.使用protocol buffer编译器生成服务器和客户端代码.使用C#gRPC API为您的服务 ...

  10. Oracle的查询-子查询

    --子查询 --子查询返回一个值 --查询出工资和scott一样的员工信息 select * from emp where sal in (select sal from emp where enam ...