C中结构体是另外一种表示数据形式的方式,结构体中可以表示C中的基本数据形式,如int,double....结构体可以让我们更好的表示数据。下面来看看结构体。

  说到结构体首先要了解的是它的申明形式,要申明一个结构体形式如下:

 #include<stdio.h>
#define LEN 20 //申明一个结构体
struct name {
char firstname[LEN];
char lastname[LEN];
}; //申明一个结构体
struct guy {
struct name handle; //结构体嵌套
char favfood[LEN];
char job[LEN];
int age;
}; int main(int argc, char* argv[])
{
........
}

  在结构体中可以有基本的数据类型例如上面的int,char数组,也可以嵌套有其他结构体,例如上面结构体guy中就存在另外一个结构体name。值得注意的是,我们在申明一个结构体的时候,计算机并没有为数据分配空间,而是在我们创建结构变量的时候才会进行分配。创建结构变量的形式如下:

struct guy new_guy;

  在计算机执行到上面这句时,计算机会为变量分配内存。如上guy中包含一个name结构体,name结构体中是由两个20个char所占字节组成,共计2*20=40字节,而favfood和job也是两个长度为20的char数组,age是一个int类型,所以一个guy类型的变量所占字节数共计为40+20+20+4=84。

  现在我们知道如何申明一个结构体和定义一个结构体变量了。先看看下面的代码:

 struct guy new_guy1 = { //结构体的初始化
{"zhou","xuanyu"},
"tomato",
"student", };
struct guy new_guy2 = { //结构体的初始化
.handle = {"zhou","xuanyu"},
.job = "student",
};

  上面一段代码是对一个结构体进行初始化,对于new_guy1,我们对它的每一个属性都初始化了,而对于new_guy2我们仅仅初始化了他的handle和job。对于一个结构体我们应该怎么访问结构体中的每一个项呢?不错,是使用 . 运算符。例如:

printf("%s",new_guy2.handle); ,就可以打印出"zhouxuanyu"。再看看下面这段代码(其中的结构体guy在上面已定义):

 int main(int argc, char* argv[])
{
struct guy new_guy[] = { //定义一个结构体数组
{
{"zhou","xuanyu"},"tomato","student", //初始化数组第一项
},
{
{"hu","jiannan"},"fruit","student", //初始化数组第二项
}
}; struct guy * him; //指向结构体guy的指针
him = &new_guy[]; //将指针指向guy数组 printf("address #1:%p, #2:%p\n",&new_guy[],&new_guy[]);
printf("pointer #1:%p, #2:%p\n",him,him+); printf("him->handle.firstname is %s,(*him).age is %d\n",him->handle.firstname,(*him).age);
him++;
printf("him->job is %s,(*him).handle.lastname is %s\n",him->job,(*him).handle.lastname);
}

  在上面这段代码中,我们定义了一个guy类型的数组,定义一个结构体数组的形式和定义一般数组一样。在上面代码第12行中我们申明了一个指向结构体的指针him,利用指针我们可以对数据的操作会更加灵活。在13行,我们初始化了这个指针,这里要注意的是结构体的名称和数组名不同,数组名就是数组其实元素的地址,所以可以这样做int *p = a,假设a是一个int类型的数组,但是结构体不行,必须使用&取地址。所用上面15,16行打印出来的地址是一样的。上面的代码中又出现了一个新的运算符->。它的作用和刚刚说的 . 运算符一样,只是作用的对象不一样,简单的记法就是:指针使用->访问结构体中的项,而结构体变量使用.访问它的项。到现在我们已经大概了解了结构体的基本用法。下面来看看结构体在函数中使用的几种方式:

 #include<stdio.h>
#define LEN 20 struct Book { //定义结构体
char bookname[LEN];
double price;
char author[LEN];
}; //三个函数都用于改变书的价格
double changebook1(double);       //因为只改变书的价格,直接将价格作为参数传入函数
double changebook2(struct Book *);   //传入一个指向Book类型的指针
double changebook3(struct Book);    //传入一个结构体 int main(int argc, char* argv[])
{
struct Book book = {
"C Primer Plus",75.0,"John"
}; struct Book * p_book = &book; printf("book's price is: %f\n",book.price);
printf("after changebook1(),return value is: %.2f, book's price is: %.2f\n",changebook1(book.price),book.price);
double new_price2 = changebook2(p_book);
printf("after changebook2(),return value is: %.2f, book's price is: %.2f\n",new_price2,book.price);
double new_price3 = changebook3(book);
printf("after changebook3(),return value is: %.2f, book's price is: %.2f\n",new_price3,book.price);
} double changebook1(double price){
return price * ;
} double changebook2(struct Book * book){
book->price *= ;
return book->price;
} double changebook3(struct Book book){
book.price *= ;
return book.price;
}

  上面的代码中,我们定义了三个函数用来改变book的价格,第一个是直接将double类型的pirce传入,第二个是将一个指向结构体的指针传入,第三个是将整个结构体传入。最后打印出函数运行之后的结构,如下:

  

  从结果可以看出,只有changebook2()函数才真正的将书的价格改变了。这是为什么呢?原因是这样的,方法二是将一个指针作为参数传入函数,指针指向的是原始数据,所以我们所做的所有操作都是在原始数据上进行的。而方法三传入的是一个结构体,在调用函数changebook3()的时候,会根据模板Book创建一个自动变量,然后这个变量的成员会被初始化与原始数据一样副本。而我们所进行的操作都是在这个副本上进行的,所以不会对原始数据有任何改变。但是这样的做法会对内存有很大的浪费,所以我们一般使用的第二种方式,但是第二种方式会有破坏数据的可能,该怎么办呢?在C中const关键字可以解决这个问题。如果我们对原始数据不需要进行修改,这时候可以将传入函数的指针用const修饰。

认识C中的结构体的更多相关文章

  1. C++中的结构体

    http://zhidao.baidu.com/link?url=8OYQSKV9mvSBc6Hkf9NsLQmipSge9VCZDJQGAZZs5PCBQ54UTmK98VRmAklEEAFYu7d ...

  2. C/C++中的结构体

    结构体定义 结构体(struct)是由一系列具有相同类型或不同类型的数据构成的数据集合,也叫结构.   结构体作用 结构体和其他类型基础数据类型一样,例如int类型,char类型 只不过结构体可以做成 ...

  3. C语言中的结构体,结构体数组

    C语言中的结构体是一个小难点,下面我们详细来讲一下:至于什么是结构体,结构体为什么会产生,我就不说了,原因很简单,但是要注意到是结构体也是连续存储的,但要注意的是结构体里面类型各异,所以必然会产生内存 ...

  4. 再识C中的结构体

    在前面认识C中的结构体中我介绍了结构体的基础知识,下面通过这段代码来回顾一下: #include<stdio.h> #define LEN 20 struct Student{ //定义结 ...

  5. C语言中的结构体和C++中的结构体以及C++中类的区别

    c++中结构体可以定义一个函数 C中的结构体和C++中结构体的不同之处:在C中的结构体只能自定义数据类型,结构体中不允许有函数,而C++中的结构体可以加入成员函数. C++中的结构体和类的异同: 一. ...

  6. 关于C语言中结构体中的结构体成员导致的字节对齐问题

    关于结构体的字节对齐是什么,就不赘述,再此附上一篇文章,介绍字节对齐:http://www.linuxsong.org/2010/09/c-byte-alignment/ 这里的结构体字节对齐的数据类 ...

  7. C语言中处理结构体的原理

    汇编中有几种寻址方式,分别是直接寻址:(ds:[idata]).寄存器间接寻址(ds:[bx]).寄存器相对寻址(ds:[bx + idata].ds:[bx + si])基址变址寻址(ds:[bx ...

  8. 浅析C#中的结构体和类

    类和结构是 .NET Framework 中的常规类型系统的两种基本构造. 两者在本质上都属于数据结构.封装着一组总体作为一个逻辑单位的数据和行为. 数据和行为是该类或结构的"成员" ...

  9. C++中的结构体的认识

    C++中的结构体的认识 1. typedef的用法 在C/C++语言中,typedef常用来定义一个标识符及关键字的别名,它是语言编译过程的一部分,但它并不实际分配内存空间. 实例像:typedef ...

  10. x264中重要结构体参数解释,参数设置,函数说明 <转>

    x264中重要结构体参数解释http://www.usr.cc/thread-51995-1-3.htmlx264参数设置http://www.usr.cc/thread-51996-1-3.html ...

随机推荐

  1. LINQ标准查询操作符(五)

    十二.相等操作符 如果两个序列的对应元素相等且这两个序列具有相同数量的元素,则视这两个序列相等. SequenceEqual方法通过并行地枚举两个数据源并比较相应元素来判断两个序列是否相等.如果两个序 ...

  2. Spark RDD概念学习系列之RDD的转换(十)

    RDD的转换 Spark会根据用户提交的计算逻辑中的RDD的转换和动作来生成RDD之间的依赖关系,同时这个计算链也就生成了逻辑上的DAG.接下来以“Word Count”为例,详细描述这个DAG生成的 ...

  3. 关于VSS配置遇到的问题及解决方法

    今天安装网上的教程开始部署源代码管理器 相关工具 VSS安装包:http://url.cn/PolkN8 VSS汉化包:http://url.cn/PeHq1A 具体安装教程请参考:http://ww ...

  4. [原创]Devexpress XtraReports 系列 3 创建主从报表

    昨天写了系列的第二篇Devexpress XtraReports 系列 2 创建表格报表 . 今天我们来继续系列 3 创建主从报表 首先我们来看看最后实现的效果.Demo最后附上. 开始吧. 第一步, ...

  5. Hibernate入门(2)- 不用配置用注解

    在上一个例子里面,我用的配置文件的方式,这次改成注解. pom.xml 增加了hibernate-commons-annotations和hibernate-annotations <proje ...

  6. linux 下查找大于100M的文件

    命令行如下 find . -type f -size +100M Linux系统下查找大文件或目录的技巧 当硬盘空间不够时,我们就很关心哪些目录或文件比较大,看看能否干掉一些了,怎么才能知道呢?以易读 ...

  7. spring mvc中的valid

    当你希望在spring mvc中直接校验表单参数时,你可以采用如下操作: 声明Validator的方式: 1.为每一个Controller声明一个Validator @Controller publi ...

  8. Python基础 字符串的魔法

    capitalize(self) 返回值:将字符串的第一个首字母变成大写,其他字母变小写 s = 'hello World' ss = s.capitalize() print(ss) Hello w ...

  9. HDU 5164Matching on Array(AC自动机)

    这是BC上的一道题,当时比赛没有做,回头看看题解,说是AC自动机,想着没有写过AC自动机,于是便试着抄抄白书的模板,硬是搞了我数个小时2000ms时限1800过了= = ! 这里就直接贴上BC的结题报 ...

  10. hdoj 5358 First One

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5358 一开始一直以为是一道数学题,在找有什么规律化简Log2(S(i,j)),结束了以后才造  ⌊lo ...