【408】C语言:构造类型-数组

20240629ky学习笔记自用

数据类型--构造类型(数组、结构体)

场景特点:

  • 数据类型相同

  • 使用过程需要保留原始数据?

声明数组

  • 命名规则遵循标识符命名规则(即和命名变量名相同)。

  • 方括号中的最好是常量表达式,表示数组长度。

  • 常量表达式:常量和符号常量,不能包括变量。也就是C语言不允许对数组的大小做动态定义。

int n=10;
int a[n]; //老式的是不行的,请你机试时候不要这样用。

int a[10];
  • 数组长度大小为0没有意义。方括号不能写成圆括号。不能用变量声明数组大小。

初始化数组

  • int a[10]={1,2,3,4,5}; 其余没有赋值的自动为0.

  • 全为0,可以写int a[10]={0};

  • int a[]={1,2,3,4,5},计算机会自动识别长度为5。但是初始不建议,乖乖写上就好。

  • 不能写成int a[10]; a[10]={1,2,3,4,5,6,7,8,9,10}

数组的访问越界

  • 操作系统对内存中的每个位置也给予了编号,对于windows32位控制台应用程序而言,编号就是从0x 00 00 00 00到0xFF FF FF FF,总计2的32次方,大小为4G。

  • 访问越界,c语言不会检查你的越界,需要自己注意!

#include <stdio.h>

int main() {
    int a[5]={1,2,3,4,5};
    int j=20;
    int i=10;
    a[0]=-1;
    a[5]=6; //访问越界,c语言不会检查你的越界
    a[6]=7;
    printf("a[0]=%d\n",a[0]);
    printf("i=%d\n",i);//i竟然发生改变。

    return 0;
}

数组传递

  • 数组名传递到子函数后,子函数的形参接收到的是数组的起始地址,8个字节。

  • 数组的长度是传递不过来的。

  • 子函数内可以改变数组的值。

  • 对传递数组的函数,print(a,5);  

    • 不要写a[5],这样是访问第6个元素,访问越界。

    • 也不要写a[]。

#include <stdio.h>
//子函数把某一个常用功能封装起来。
//子函数传递不来数组长度,所以需要多一个length参数。
void print(int a[5],int length) //这里不用写5,数组的长度是传递不过来的。这里写b也行,不用同步主函数里面的a。
{
    int i;
    //数组名传递到子函数后,子函数的形参接收到的是数组的起始地址,8个字节。(64位)
    //所以不能把数组的长度传递给子函数。所以sizeof(a)得到的会是8.
//    for(i=0;i<sizeof(a)/sizeof(int);i++)
//    for(i=0;i<5;i++)
    for(i=0;i<length;i++)
    {
        printf("%3d",a[i]);
    }
    a[3]=20;  //子函数内可以改变数组的值。
    printf("\n");
}

//main函数就是主函数。
int main() {
    int a[5]={1,2,3,4,5};
//    print(a);
//这里不要写a[5],这样是访问第6个元素,访问越界。
//也不要写a[]。
    print(a,5);
    printf("%3d\n",a[3]);
    return 0;
}

字符数组

初始化

  • 使用%s来输出一个字符串,直接把字符数组名放在printf后面的位置。

  • 初始化1:每一个字符必须要用单引号引起来,但是这样没有结束符,用%s输出的时候会出现乱码!

  • 初始化2:双引号。注意c语言规定字符串的结束标志为'\0'。所以char a[10]最长存储9个字符,剩余一个存'\0'。

#include <stdio.h>

//模拟printf输出%s情形
void print(char a[])
{
    int i=0;
//    while(a[i]!='\0')也可以
    while(a[i])// 当走到结束符时,循环结束。
    {
        printf("%c",a[i]);
        i++;
    }
    a[0]='H';
    printf("\n");
}
//字符数组
int main() {
    char c[3]={'d','a','b'};//每一个字符必须要用单引号引起来,但是这样没有结束符,用%s输出时候会出现乱码!!!
    char a[6]={"hello"};//使用这种方式初始化。不要写成a[5]!!!
    char b[5]={"hello"};
    print(a);
    printf("%s\n",a);//使用%s来输出一个字符串,直接把字符数组名放在printf后面的位置。
    printf("%s\n",c);//有乱码
    printf("%s\n",b);//有乱码
    return 0;
}

scanf字符串

  • 字符数组名c中本来就存储了数组的起始地址,因此不需要取地址!!!

  • scanf的%s输入完成后会自动填一个'\0'进去。

  • sacnf的%s读到空格也不会继续往下读。

  • scanf的%s%s读到空格,就开始匹配第二个%s,但是会清除读到的那个空格,和%d、%f一样会忽略空格。

  • sacnf的%c读到空格会存储,反正记得连续输入时在%c前面要加一个空格。

#include <stdio.h>
int main() {
    char c[10]={'1','2','3','4','5','6','7','8'};
    char a[10],b[10],i[10],j[10];
    int d,k;
    char g,m;
    float f,h;
    scanf("%s",c);//字符数组名c中本来就存储了数组的起始地址,因此不需要取地址。
    //sacnf的%s读到空格也不会继续往下读。
    //scanf的%s%s读到空格,就开始匹配第二个%s,但是会清除读到的那个空格,和%d、%f一样会忽略空格。
    //sacnf的%c读到空格会存储?反正记得在%d和%c之间要加一个空格。
    fflush(stdin);
    scanf("%s%s",a,b);
    fflush(stdin);
    scanf("%s %s",i,j);
    fflush(stdin);
    scanf("%d%f%c",&d,&f,&g);
    fflush(stdin);
    scanf("%d%f %c",&k,&h,&m);
    //scanf输入完成后会自动填一个'\0'进去。
    printf("c=%s\n",c);
    printf("a=%s,b=%s\n",a,b);
    printf("i=%s,j=%s\n",i,j);
    printf("dfc=%d,%f,%c\n",d,f,g);
    printf("df c=%d,%f,%c\n",k,h,m);
    return 0;
}

gets函数、puts函数

char *get(char *str);
int puts(char *str);

  • puts等价于printf("%s\n",c);

  • puts内放的参数是字符数组名。

  • gets中放入我们字符数组的数组名即可。

  • gets读到'\n'就不读,然后会在数组最后存上'\0'.

  • windows下使用VS的集成开发环境,不能使用gets,使用fgets(c,sizeof(c),stdin);

#include <stdio.h>

int main() {
    char c[20];
    gets(c);//gets中放入我们字符数组的数组名即可。
    //gets读到'\n'就不读,然后在数组最后存上'\0'
    puts(c);//puts等价于printf("%s\n",c);
    //puts内放的参数是字符数组名。
    return 0;
}

str系列字符串操作函数

  • strcpy、strcat、strcmp、strlen都可以放字符串常量。

  • 但是strcpy、strcat第一个位置要放空间,不能放字符串常量。

  • strlen统计字符串长度,但是不会统计'\0'。

  • strcmp(a,b):a大于b,返回的是正值;相等是0;a小于b,返回负值。

#include <stdio.h>
#include <string.h>
int mystrlen(char c[])
{
    int i=0;
    while(c[i])//找到结束符后,循环结束。
    {
        i++;
    }
    return i;
}
int main() {
    char c[20],d[100]="world";
    char e[100];
    int len;
    gets(c);
    puts(c);
    len=strlen(c);//统计字符串长度,不会统计'\0'
    printf("len=%d",len);
    len=mystrlen(c);
    printf("my len=%d",len);
    
    strcat(c,d);//把d中的字符串拼接到c中。
    puts(c);
    
    strcpy(e,c);//把c中的字符串复制到e中。
    puts(e);

    printf("c?d=%d\n",strcmp(c,e));
    printf("c?d=%d\n",strcmp(c,d));
    printf("c?d=%d\n",strcmp(c,"how"));
    //c大于”how“,返回的是正值;相等是0;c小于”how“,返回负值。
    //注意比较的不是长度,是abcdef。
    
    //strcpy、strcat第一个位置要放空间,不能放字符串常量。
    //strcpy、strcat、strcmp、strlen都可以放字符串常量。
    return 0;
}

题目

输入n个数,出现2的次数

  • 注意开始的count需要初始化为0!!

#include <stdio.h>

int main() {
    //输入n个数,出现2的次数
    int length,i;
    int arr[100];
    scanf("%d",&length);
    for(i=0;i<length;i++)
    {
        scanf("%d",&arr[i]);
    }

    int count=0;
    for(i=0;i<length;i++)
    {
        if(arr[i]==2)
        {
            count++;
        }
    }
    printf("%d\n",count);
    return 0;
}

逆转之后判断大小,原字符更大则输出1.

  • 可以直接在vers[100]={0},初始化!存上结束符!!

  • 注意对于strcmp输出的是负数,不一定就是-1.

#include <stdio.h>
#include <string.h>
int main() {

    //逆转之后判断大小,原字符大输出1.
    char c[100];
    gets(c);
    char vers[100];
    int i=strlen(c),j=0,result;

    vers[i]='\0';  //可以直接在vers[100]={0},初始化!
    while(i)
    {
        i--;
        vers[j]=c[i];
        j++;
    }
    //可以使用for循环
//    for(i=0;j=strlen(c);i++,j--)
//    {
//        vers[j]=c[i];
//    }
//    printf("%s\n",c);
//    puts(vers);
    //注意对于strcmp输出的是负数,不一定就是-1.
    result=strcmp(c,vers);

    if(result>0)
    {
        result=1;
    }else if(result<0){
        result=-1;
    }else{
        result=0;
    }
    printf("%d\n",result);
    return 0;
}

  • 17
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值