浅谈字符数组

article/2025/9/1 14:43:09

文章目录

  • 一、什么是字符数组
  • 二、字符数组的定义和赋值
    • 1. 先定义一个数组,再为挨个元素进行赋值
    • 2. 在定义的同时给该字符数组进行初始化
      • 2.1 错误的初始化方式
      • 2.2 正确的初始化方式
    • 3. 特别注意!!!
      • 3.1 字符数组和整型数组一样不支持隔语句初始化!!!
  • 三、字符串处理函数
    • 3.1 gets(字符数组)
    • 3.2 puts(字符数组)
    • 3.3 strcat(字符数组1,字符串2)
    • 3.4 strcmp(字符串1,字符串2)
    • 3.5 strlen(字符数组)
    • 3.6 strlwr(字符串)和strupr(字符串)
  • 四、字符数组和字符指针
    • 4.1 字符型指针
    • 4.2 字符指针作函数参数
    • 4.3 调用函数时实参与形参的对应关系
    • 4.4 字符指针和字符数组的差别
  • 五、多维数组的字符指针
  • 六、多重指针

一、什么是字符数组

  • 字符数组就是建立一连串的字符存储空间用来存储字符,多个字符也就形成了字符串。
  • 字符数组中的一个元素用来存放一个字符,数组定义、元素赋值等操作类似于整形数组,但是字符数组的赋值方式多了一种(下面详细讲)

二、字符数组的定义和赋值

1. 先定义一个数组,再为挨个元素进行赋值

这种定义方式的缺点是挨个赋值的代码量太多,没有太多意义,降低了可读性。

char c[10];
c[0]=’I’;   c[1]=’ ’;
c[2]=’a’;   c[3]=’m’;
c[4]=’  ’;   c[5]=’h’; 
c[6]=’a’;  c[7]=’p’; 
c[8]=’p’;  c[9]=’y’;

存储的结构如下:
字符数组存储方式

2. 在定义的同时给该字符数组进行初始化

2.1 错误的初始化方式

//错误的初始化方式:
char c[10]={’I’,’ ’,’a’,’m’,’ ’,’h’,’a’,’p’,’p’,’y’};

存储的结构如下:
在这里插入图片描述

注意: 该赋值的方式是错误的,因为如果不是用字符串的形式命名,需要在结尾加一个’\0’。

2.2 正确的初始化方式

//正确的初始化方式
char c[10]={’c’,’ ’,’p’,’r’,’o’,’g’,’r’,’a’,’m’,0};

存储的结构如下:在这里插入图片描述

重点:
*对比了正确的初始化方式和错误的初始化方式,我们可以从他们对应的存储结构上看到,正确的初始化方式多个’\0’。

为什么少了个’\0’就会差别这么呢?
这就涉及了字符串和字符串结束标志
(1)在C语言中,是将字符串作为字符数组来处理的
(2)关心的是字符串的有效长度而不是字符数组的长度 (有效长度 == 实际长度)
(3)为了测定字符串的实际长度,C语言规定了字符串结束标志 ’\0’
(4)’\0’代表ASCII码为0的字符
(5)从ASCII码表可以查到,ASCII码为0的字符不是一个可以显示的字符,而是一个“空操作符”,即它什么也不做。用它作为字符串结束标志不会产生附加的操作或增加有效字符,只起一个供辨别的标志

其实相对于上面的正确初始化方式,还有一种将整个字符串赋值给字符数组,代码如下:

char c[]={'I',' ','a','m',' ','h','a','p','p','y'};
//如上的定义初始化方式可以写成下面的三种形式
char c[]={"I am happy"};
//可写成
char c[]="I am happy";
//相当于
char c[11]={"I am happy"};

加深类比:

char c[10]={”China”};
//可写成
char c[10]=”China”;
//从c[5]开始,元素值均为\0

在这里插入图片描述

3. 特别注意!!!

3.1 字符数组和整型数组一样不支持隔语句初始化!!!

代码如下:

    //此种定义了整型数组后,对他再赋值的方式是错误的!!!int a[4] = {1};a = { 1,2,3,5,6 };//此种定义了字符数组后,对他再赋值的方式是错误的!!!char c[5] = { 'a' };c = { 'a','b','c' };

三、字符串处理函数

在程序中往往需要对字符串作某些操作处理,两个字符串连接、两个字符串进行比较等在C函数库中提供了一些字符串处理函数,使用很方便。

函数作用
gets(字符数组)从终端输入一个字符串到字符数组
puts(字符数组)将一个字符串(以’\0’结束的字符序列)输出到终端
strcat(字符数组1,字符数组2)连接两个字符数组中的字符串把字符串2接到字符串1的后面
strcpy(字符数组1,字符串2)将字符串2复制到字符数组1中去
strcmp(字符串1,字符串2)比较串1和串2。若串1=串2,则函数值为0;若串1>串2,则函数值为一个正整数;若串1<串2,则函数值为一个负整数
strlen(字符数组)测试字符串长度
strlwr(字符串)将字符串中大写字母换成小写字母
strupr(字符串)将字符串中小写字母换成大写字母

3.1 gets(字符数组)

其一般形式为:strlen (字符数组);它是测试字符串长度的函数,函数的值为字符串中的实际长度。如: gets(str); Computer↙

3.2 puts(字符数组)

puts函数(输出字符串函数)其一般形式为: puts (字符数组);作用是将一个字符串输出到终端,如: char str[20]=”China”;puts(str); 输出China。

3.3 strcat(字符数组1,字符串2)

strcat函数(字符串连接函数)其一般形式为:strcat(字符数组1,字符数组2);其作用是把两个字符串连接起来,把字符串2接到字符串1的后面,结果放在字符数组1中。

char str1[30]=”People”;
char str2[]=”China”;
printf(%s”, strcat(str1,str2));  
//输出:PeopleChina

3.4 strcmp(字符串1,字符串2)

比较的结果由函数值带回
如果字符串1=字符串2,则函数值为0
如果字符串1>字符串2,则函数值为一个正整数
如果字符串1<字符串2,则函数值为一个负整数

3.5 strlen(字符数组)

char str[10]=”China”;
printf(”%d”,strlen(str));
输出结果是5
也可以直接测试字符串常量的长度
strlen(”China”);

3.6 strlwr(字符串)和strupr(字符串)

其返回值是一个字符指针类型
(1)其一般形式为strlwr (字符串);函数的作用是将字符串中大写字母换成小写字母
(2)其一般形式为strupr (字符串);函数的作用是将字符串中小写字母换成大写字母


四、字符数组和字符指针

4.1 字符型指针

字符型指针用char*定义,它不仅可以指向一个字符型常量,还可以指向一个字符串。

char str[] = "I am happy";
char* c = str;

此时c变量就是存储了str数组的第一个元素的地址,代码如下:

在这里插入图片描述

4.2 字符指针作函数参数

(1)如果想把一个字符串从一个函数“传递”到另一个函数,可以用地址传递的办法,即用字符数组名作参数,也可以用字符指针变量作参数。
(2)在被调用的函数中可以改变字符串的内容
(3)在主调函数中可以引用改变后的字符串

例子如下:
例子1:有一字符数组a,内存有字符串"I am a boy.",要求把该字符串复制到字符数组b中。(要求用函数完成实现)
在这里插入图片描述
例子2:有字符串a=“I am a teacher.”, 字符串b=“You are a student.”,要求把字符串b连接到字符串a的后面。即字符串a的内容为“I am a teacherYou are a student.”
在这里插入图片描述

4.3 调用函数时实参与形参的对应关系

在这里插入图片描述

4.4 字符指针和字符数组的差别

虽然用字符数组和字符指针变量都能实现字符串的存储和运算,但它们二者之间是有区别的,不应混为一谈。主要有以下几点:
(1)字符数组由若干个元素组成,每个元素中放一个字符,而字符指针变量中存放的是地址(字符串第1个字符的地址),决不是将字符串放到字符指针变量中。
(2)赋值方式:对字符数组只能对各个元素赋值,不能用以下办法对字符数组赋值:
char str[14];
str=”I love China!″; (×)
而对字符指针变量,可用下面方法赋值:
char *a;
a=”I love China!″;
但注意赋给a的不是字符,而是字符串第一个元素的地址。
(3)对字符指针变量赋初值:
char *a=”I love China!″; 等价于 char *a;a=”I love China!″;
而对数组的初始化:
char str[14]={”I love China!″};不能等价于char str[14];str[]=”I love China!″;
无论是什么数组都不支持动态赋整条数据,例如int a[];a={1,2,3,4},此赋值方式是错误的!!!
(4)如果定义了一个字符数组,在编译时为它分配内存单元,它有确定的地址。而定义一个字符指针变量时,给指针变量分配内存单元,在其中可以放一个字符变量的地址。

//第一种
char *a; scanf(%s”,a);   //错
char *a,str[10];      
//第二种
a=str;                  
scanf (%s”,a);     // 对

说人话就是,指针变量是用来存放地址的,而字符数组是在内存开辟了一个空间来存储字符的,两者的性质就不一样。scanf函数输入的是一个字符串是要放到一个存储空间里面,所以直接用一个存放指针的变量来存放一组字符串就不行了

(5)指针变量的值是可以改变的。
例如:

#include <stdio.h>
void main(){ char *a="I am Chinese!";a=a+6; printf("%s\n",a);
}

其中的char *a=“I am Chinese!”;a=a+6; 不能改成char a[]=“I am Chinese!”;a=a+6;。这里可以理解为数组名是一辆车上的司机,而字符指针变量是一个导游,元素是乘客。导游可以到处走,而司机不可以到处走。

(6)对字符数组可以用下标法和地址法引用数组元素(a[5],(a+5))。如果字符指针变量p=a,则也可以用指针变量带下标的形式和地址法引用(p[5],(p+5))。
在这里插入图片描述
(7)字符数组中各元素的值是可以改变的(可以对它们再赋值),但字符指针变量指向的字符串常量中的内容是不可以被取代的(不能对它们再赋值)。如:

char a[]="House";char *b="House";a[2]='r';   // 对b[2]='r';   // 错

因为他们存储的位置不同,传递给字符型指针的字符串是存储在常量池里面,常量池里面的数据不可以修改。

五、多维数组的字符指针

在这里插入图片描述
首先得明确一个概念数组名a的意思是指向该二维数组的第一行,而 a+1,a+2表示的是第二行和第三行。如果加了一个*,如:*a,*(a+1)+1,*(a+2)+2分别表示第一行的第一列、第二行的第二列、第三行的第三列。其中的数组名即代表第一行,也代表了第一行的第一列个元素的地址

表现形式含义地址
a一行一列元素的地址,也是第一行的地址1000
*(a+1)+1第二行第二列的元素地址1004
*( *(a+1)+1)第二行第二列的元素值值:5

特别注意:
(1)如果是用指针变量去读取数据,就只需一个*号就可以读取数据,因为指针与数组名不同,他就只是指向地址,所以只需要考虑地址位置就可以读取地址里面的值,而数组名不一样,他代表了一个数组的层次关系,它是一个数组的队头。例如二维数组中,既要表清楚行和列,所以需要a表示第一行,*a表示第一行第一列。
在这里插入图片描述
(2)用数组名去取值
在这里插入图片描述
在这里插入图片描述

六、多重指针

在这里插入图片描述


http://chatgpt.dhexx.cn/article/lA37k0AJ.shtml

相关文章

字符数组

字符数组 用来存放字符数据的数组是字符数组。字符数组中的每一个元素存放一个字符&#xff0c;其定义和使用方法与其他类型的数据基本相似。 1.1字符数组的定义和使用 字符数组的定义与其他类型的数组类似&#xff0c;标准形式如下&#xff1a; Char 数组名 【常量表达式】 …

Stata:嵌套Logit模型(NestedLogit)

原文链接&#xff1a;https://www.lianxh.cn/news/d5e00bfb17a7c.html 致谢&#xff1a; 这篇推文的核心内容主要来自陈强老师编著的《高级计量经济学及 Stata 应用》一书&#xff0c;特此致谢。 1. 简介 此前&#xff0c;连享会发布了一系列离散选择模型相关的推文&#xff0…

MNL——多项Logit模型学习笔记(二)

本节将会通过案例举例&#xff0c;介绍Logit模型的建模思路和过程 内容为摘抄他人学习资料的个人学习笔记&#xff0c;如有侵权则删 1.正确打开/解读Logit模型系数的方式 本节的具体内容在笔记里不详细表示了&#xff0c;大家在软件里拟合Logit模型时&#xff0c;对于其中的参…

logit回归模型的参数估计过程_【DCM07】Random Parameter(随机参数)Logit模型及其Nlogit实现...

本文是离散选择模型系列的第7篇原创文章,将详细介绍随机参数Logit模型,并利用Nlogit软件进行实操演示。【关注本公众号,可以获取数据和代码】本文公式较多,建议电脑端享用。 目录 1、随机参数Logit模型介绍 2、数据描述 3、随机参数Logit模型的参数估计 1 随机参数Logit模型…

MNL——多项Logit模型学习笔记(三)二项Logit模型、Gumble分布以及Logistic分布

上一节最后一部分&#xff0c;介绍了Provit模型&#xff0c;从建模的角度来说&#xff0c;Probit模型假设随机项服从正态分布&#xff0c;这是具有一定的合理性的——也是其优点&#xff1b;但是Probit模型没有闭合解——每次算P(n)i 的值的时候都需要求积分&#xff0c;这就给…

模型与logit_互助问答第33期:条件logit模型相关问题

问题: 尊敬的老师,您好!我最近在做一个条件logit模型的实证研究,因为是非线性的二元响应模型,查了很久的文献和Stata资料也没找到检查这类模型异方差的方法以及处理异方差的办法,请您们帮忙分析下,谢谢!如果可以的话,希望您能给出Stata命令,再次感谢! 答案: 第一,…

logit模型应用实例_互助问答第240期:面板Logit模型

您好老师,我是暨南大学国际商务专业的一名应届毕业生,有一个问题思考了很久都没办法解决,所以想要向你们求助。具体情况如下:我的论文采用的是面板logit模型,在判断使用固定效应和随机效应的过程中,我分别用命令xtlogit y x1 x2 x3,fe和xtlogit y x1 x2 x3,re得到了固定…

Logit模型和Logistic模型

一、离散选择模型&#xff08;Discrete Choice Model, DCM&#xff09; 常见的DCM模型&#xff1a;二项Logit&#xff08;Binary Logit&#xff09;、多项Logit&#xff08;Multi-nominal Logit&#xff09;、广义Logit&#xff08;Generalized Logit&#xff09;、条件Logit&a…

logit回归模型_是或否,Logit模型详解以及论文实践

目录 1.Logit和Probit的模型差别 2.二分类Logistic回归模型 3.多分类Logistic回归模型 4.次序Logistic回归模型 5.面板数据Logistic回归模型 Logit回归(又称逻辑回归、罗杰斯蒂回归、Logistic回归)无疑是社会科学,尤其是社会学研究中使用最广的方法,没有之一。这也是因为…

【Python计量】Logit模型

文章目录 一、离散选择模型二、Logit模型三、Logit模型的python实现——采用statsmodels&#xff08;一&#xff09;案例一&#xff08;二&#xff09;案例二 此文章首发于微信公众号Python for Finance 链接&#xff1a;https://mp.weixin.qq.com/s/EeT84koL1ZAAQe5yZALuzw 一…

OGNL表达式学习笔记

OGNL表达式是一个独立的语言&#xff0c;strut2将其引入共同构造struts2。 OGNL语言强大于EL表达式&#xff0c;其可以访问java类中的对象&#xff0c;也可以访问对象的静态方法。 public class OgnlDemo1 {Testpublic void test1() throws OgnlException{OgnlContext contex…

ognlognl表达式 研究

为了解决数据从View层传递到Controller层时的不匹配性&#xff0c;Struts2采纳了XWork的OGNL方案。并且在OGNL的基础上&#xff0c;构建了OGNLValueStack的机制&#xff0c;从而比较完美的解决了数据流转中的不匹配性。 OGNL&#xff08;Object Graph Navigation La…

ognl表达式的研究

OGNL —— 完美的催化剂 为了解决数据从View层传递到Controller层时的不匹配性&#xff0c;Struts2采纳了XWork的OGNL方案。并且在OGNL的基础上&#xff0c;构建了 OGNLValueStack的机制 &#xff0c;从而比较完美的解决了数据流转中的不匹配性。 …

OGNL表达式原理及使用

OGNL &#xff1a;object graph navigation language&#xff0c;对象图形导航语言&#xff0c;一种表达式语言。 为什么出现&#xff1a; 在我们所熟悉的mvc框架中&#xff0c;数据是在各层之间进行流转使用的。 显示层&#xff1a;将数据展示给用户&#xff0c;数据…

OGNL表达式的介绍

OGNL OGNL的简介OGNL与EL表达式的区别OGNL案例OGNL向ValueStack压栈 OGNL的简介 OGNL是对象 - 图形导航语言&#xff08;Object Graph Navigation Language&#xff09;的缩写&#xff0c;它是一种功能强大的表达式语言&#xff0c;通过它简单一致的表达式语法&#xff0c;可以…

Arthas--ognl表达式

背景 arthas执行ognl表达式&#xff0c;获取对应的jvm对象数据。ognl学习&#xff0c;可以查看上篇&#xff1a;https://xiaopanjia.blog.csdn.net/article/details/130425414 基本语法 ognl express -c {hashCode} --classLoaderClass {当前的全路径 ClassLoader 信息} -x …

OGNL表达式语言详解

众所周知&#xff0c;OGNL充斥在Struts2前后台数据传递与存储的方方面面&#xff0c;给Struts2中数据的处理带来了极大的方便&#xff0c;所以&#xff0c;本次打算以两篇博客来介绍OGNL&#xff0c;第一篇就是脱离MVC框架&#xff0c;单纯介绍OGNL的一般用法和语法&#xff0c…

计算机的系统总线

系统总线及控制 一、总线的基本概念1、总线定义2、信息传送方式3、总线结构 二、总线的分类根据总线的位置进行分类 三、总线特性及性能指标1、总线特性2、总线的性能指标 四、总线结构1、单总线结构2、多总线结构(1) 双总线结构(2) 三总线结构(3) 三总线结构的另一种形式(4) 四…

总线——概念与分类

文章目录 总线的定义为什么要用总线&#xff1f; 总线的特点总线的特性总线的分类串行总线与并行总线串行总线优缺点 并行总线优缺点 按总线功能1. 片内总线2. 系统总线3. 通信总线&#xff08;外部总线&#xff09;补&#xff1a;系统总线的结构单总线结构双总线结构三总线结构…

计算机系统总线

申明&#xff1a;这篇文章是我学习了哈尔滨工业大学计算机科学与技术系刘宏伟老师的mooc课程&#xff08;参考教材为高教出版社出版的唐朔飞老师编写的《计算机组成原理&#xff08;第二版&#xff09;》&#xff09;的课堂笔记整理&#xff08;系统总线部分&#xff09;&#…