C语言中的一维数组和二维数组

    选择打赏方式

数组-简单数组

概念

一组相同类型的元素的合集

一维数组的创建

int main()
{
    //创建一个存放10个元素的数组
    int arr[10] = {};
} 

数组的初始化

创建数组的时候就给数组一些数

int main()
{
    int arr[10]={1,2,3};//不完全初始化,剩下的数组初始化为0
    char arr2[10]={'a','b'}//000
    //......
} 
 strlen和sizeof没有具体的关联
    strlen是求字符串长度的-只能针对字符串求长度-是一个库函数-使用得引头文件\0之前的字符长度
    sizeof是计算:变量,数组,类型的大小,-单位是字节-是操作符 

一维数组的访问

一维数组中 a[i] 中的 a 代表了本数组的首地址,相当于 &a[0]。因此 a 就等于 a[0]。那么对 a 加 1,就可以访问下一位:(a+1) 就等于 a[1]。
访问一维数组首地址:a = &a[0];
访问一维数组的元素:a[i] = *(a+i);
输出一维数组:puts(a); //a为字符串首地址

一维数组在内存中的存放

#include<stdio.h>
int main()
{
    int arr[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
    int sz = sizeof(arr) / sizeof(arr[0]);//求数组中元素个数
    int i;
    int *p = arr;//指针变量p中存放arr[]首元素的地址
    for (i = 0; i < sz; i++)
        //printf("%p\n",&arr[i]);**打印出数组中各元素的地址,为了更直观的感受 修改一下printf里的内容**
        printf("arr[%d]=%p",i,&arr[i]);
} 

20201201231623690.png
相邻元素正好差4个字节也就是一个整型,这恰恰能说明数组在内存中是连续存放的。既然是连续存放 那么我们只要知道数组名(数组名是数组中存放首元素的地址),那么就可以找到所有元素的地址。(运用指针)

//修改一下刚才的代码
#include<stdio.h>
int main()
{
    int arr[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
    int sz = sizeof(arr) / sizeof(arr[0]);//求数组中元素个数
    int i;
    int *p = arr;
    for (i = 0; i < sz; i++)
        printf("arr[%d]=%p<===>%p\n",i,&arr[i],p+i);
} 

20201201232527196.png

  1. 我们可以看到p+i 每次i变化1,但是效果上变化了4,所以对于整型的指针变量来说+1是跳过了一个元素。由此也可以得出,指针变量的+1(p+1)与普通变量的+1 int a;(a+1)是不可以类比的;而且*(p+i)指向的就是首元素后的第i个元素。
  2. 数组在内存中存放顺序随着下标的增长地址由低到高变化

二维数组

int main()
{
    int arr[3][4] = {1,2,3,4};//存放3行4列
} 

在初始化的时候不能省略列,只能省略行

二维数组的使用

二维数组在内存中的存放

8a15aa55996845b296babf04ce2f3a91.jpg

提示:二维数组也是按照像一维数组那样的存储.
注意:如何证明:通过指针来进行访问每一个元素(*a+1)

  1. *a 表示将一个行地址变成该行的首地址(即一个具体元素的地址))
  2. &a[0][1]表示讲一个具体的元素地址 提升为该行的行地址(*与&转换关系相反)
int main()
{
    int a[3][4];
    int i, j;
    for (i = 0; i < 3; i++)
    {
        for (j = 0; j < 4; j++)
        {
            a[i][j] = i * 4 + j;
        }
    }
    for (i = 0; i < 12; i++)
    {
        printf("a[%d]=%d\n", i,*(*a+i));
    }

    system("pause");
    return 0;

} 

二维数组的访问

假设有 a[2][2] 这样一个二维数组,可以这么理解它:a 由 a[0],a[1],a[2] 构成,而 a[0] 又由 a[0][0],a[0][1],a[0][2] 构成,a[1] 由 a[1][0],a[1][1],a[1][2] 构成,a[2] 由 a[2][0],a[2][1],a[2][2] 构成。

  1. a 由 a[0],a[1],a[2] 构成,而 a[0] 又由 a[0][1],a[0][1],a[0][2] 构成;
    两个一维数组构成了一个二维数组。a 是一个二维数组,a[i] 是一个一维数组。既然 a[i] 是一个数组,那么数组名就是这个数组的首地址。比如,a[0] 就等同于 &a[0][0]。
  2. a 是一个数组名,它有三个元素:a[0],a[1],a[2];* a 等于 a[0],(a + 1) 等于 a[1],( a + 2 )等于 a[2];a[0], a[1], a[2] 又都是各个一维数组的首地址。比如 a[0] 就等同于 &a[0][0],就是说 *a[0] = a[0][0]。
    再结合上面的 *a 等于 a[0],可以得出:**a 等于 a[0][0]。
    以a[2][2]为例,则指针与数组的等价关系为:
  3. 简单记之,二维数组 a[i][j] 中的 a[i] 是一个一维数组名,也就是一个地址量。
    访问二维数组的各个字符串首地址:a[i] = &a[i][0] = *(a+i)
    访问二维数组的各个元素:a[i][j] = *(a[i] + j) = ((a+i)+j)
    输出二维数组中的一个字符串:puts(a[i]); //a[i]为字符串的首地址
    访问字符串数组
    通常对字符串的处理,传入的的参数都是字符串的首地址,也就是字符串名。
    比如:
    char s[80]; // 定义一个长度为 80 的字符串 s
    char t[80]; // 定义一个长度为 80 的字符串 t
    gets (s); // 读入一个字符串
    puts (s); // 输出一个字符串
    strcpy (s, t); // 将字符串 t 拷贝到 字符串 s 中
    其中的 s 都是该字符串的首地址。
    那相对于二维数组而言,
    char *s[] = "I", "love", "you"};
    //输出"love"
    puts (s[1]); //字符串形式 - s[1]是一个地址量,代表"love",为"love"字串的首地址
版权声明:若无特殊注明,本文为《若离风》原创,转载请保留文章出处。
本文链接:https://www.rlfit.cn/post-25.html
正文到此结束

热门推荐

发表吐槽

你肿么看?

你还可以输入 250 / 250 个字

嘻嘻 大笑 可怜 吃惊 害羞 调皮 鄙视 示爱 大哭 开心 偷笑 嘘 奸笑 委屈 抱抱 愤怒 思考 日了狗 胜利 不高兴 阴险 乖 酷 滑稽

评论信息框
可使用QQ号实时获取昵称+头像

私密评论

吃奶的力气提交吐槽中...


既然没有吐槽,那就赶紧抢沙发吧!