数组、结构体都是自建的数据结构,二者是相似的,都表示一组数据的集合,但也有区别,其区别是:

1、 数组内部数据类型相同,结构体内部数据可以不同;

2、数组按下标访问,结构体因为数据类型不同,因此数据存储大小不同,所以不能按照下标访问,只能使用运算符+元素名来访问;

 

数组:

属于构造数据类型。一个数组可以分解为多个数组元素,这些数组元素可以是基本数据类型或是构造类型。因此按数组元素的类型不同,

数组又可分为数值数组、字符数组、指针数组、结构数组等各种类别。

1、数值数组

  如:int a[10]; 说明整型数组a,有10个元素。
    float b[10],c[20]; 说明实型数组b,有10个元素,实型数组c,有20个元素。

数组的一般形式为: 类型说明符 数组名 [常量表达式],……;

其中,类型说明符是任一种基本数据类型或构造数据类型。 数组名是用户定义的数组标识符。

方括号中的常量表达式表示数据元素的个数,也称为数组的长度。C语言中不允许未知长度的数组定义,

在程序编译时,数组的长度是计算好的,即不允许定义 int a[n];类型的数组。

数组元素的表示方法为数组名+下标变量,如 a[5], a[i + j], a[i++]等。

 

C语言对数组的初始赋值还有以下几点规定:
1.可以只给部分元素赋初值。当{ }中值的个数少于元素个数时,只给前面部分元素赋值。例如: static
int a[10]={0,1,2,3,4};表示只给a[0]~a[4]5个元素赋值,而后5个元素自动赋0值。
2.只能给元素逐个赋值,不能给数组整体赋值。 例如给十个元素全部赋1值,只能写为: static int a[10]={1,1,1,1,1,1,1,1,1,1};而不能写为: static int a[10]=1;
3.如不给可初始化的数组赋初值,则全部元素均为0值。
4.如给全部元素赋值,则在数组说明中, 可以不给出数组元素的个数。例如:
static int a[5]={1,2,3,4,5};可写为: static int
a[]={1,2,3,4,5};动态赋值可以在程序执行过程中,对数组作动态赋值。 这时可用循环语句配合scanf函数逐个对数组元素赋值。

 

2、字符数组

exmple:

char str[] = "hello world";

数组首地址即为数组指针,在对str求长度时,strlen()求的结果为11,sizeof()结果为12;

因为在字符数组后默认添加字符 '\0'表示数组结束标志。

 

3、二维数组

example:

int  a[2][3]; 表示2行3列六个数值;

在按行排列的硬件中,二维数组先满足列元素分配,不足补0;

如数组a[2][3] = {1, 2, 3, 4, 5, 6, 7};

其表示a[2][3] = {

{1, 2, 3}, {4, 5, 6}, {7, 0, 0}

};

 

结构体:

在实际问题中,一组数据往往具有不同的数据类型。例如, 在学生登记表中,姓名应为字符型;学号可为整型或字符型; 年龄应为整型;性别应为字符型;成绩可为整型或实型。 显然不能用一个数组来存放这一组数据。 因为数组中各元素的类型和长度都必须一致,以便于编译系统处理。为了解决这个问题,C语言中给出了另一种构造数据类型——“结构”。“结构”是一种构造类型,它是由若干“成员”组成的。 每一个成员可以是一个基本数据类型或者又是一个构造类型。 结构既是一种“构造”而成的数据类型,
那么在说明和使用之前必须先定义它,也就是构造它。如同在说明和调用函数之前要先定义函数一样。

example:

static std{
  char name[10];
  int age;
  char sex;
  float record;
};

 

访问结构体成员时使用运算符 .或者 ->,

即 std.name    std.age

若是指向结构体指针的话只能使用->,

static std *p;

p->name        p->age

定义结构体时不一定需要有结构体名字,如

static {
  char name[10];
  int age;
  char sex;
  float record;
};