c语言块连接实现比较串大小,C语言入门语法

一、数据类型

常量

1、通过预处理声明常量#include #define PRICE 100int main() {    printf("价格:%d\n",PRICE);    return 0;

}

2、通过 const 关键字声明常量#include const int NUM=10;int main() {    printf("数量:%d\n",NUM);    return 0;

}

区别:#define 在运行时会替换为指定的值,const可以看到数据类型,更推荐使用 const

整型

在C语言中分为有符号和无符号整型,无符号是整数,有符号包含负数类型说明short2字节

int4字节

long32位系统4字节,64位系统8字节

long long8字节int main() {    int a=10;    int b=-10;    long long c=20;    int d=0b111;//二进制

int e=0xb;//十六进制

int f=010;//八进制

unsigned int g=12;//无符号正数

printf("a=%d,b=%d,c=%d,d=%d",a,b,c,d);    return 0;

}0b 为二进制方式赋值

0x 为十六进制数据

0 为八进制数据进制相关知识参考其他教程

c11 标准 stdint.h 对数据的长度进行了统一类型说明int8_t统一8位1字节

int16_t2字节

int32_t4字节

int64_t8字节

uint8_t无字符1字节

浮点数类型说明float单精度,4字节,32位

double双精度,8字节,64位

long double长双精度,16字节,128位

typedef 自定义类型typedef uint8_t mychar;int main() {

mychar ch='a';    printf("%c",ch);    return 0;

}自定义类型相当于对类型起了个别名

二、goto 跳转

使用 goto 实现循环int i=0;

aa:printf("%d\n",i);

i=i+1;if(i<100){    goto aa;

}标签名: 标记一个位置,goto 标签名; 跳转到指定标签位置,标签名可以自己定义。

三、输入与输出

1、字符输出

putchar:写字符到标准输出,相当于调用 putc

遍历字符并打印#include int main() {    char c;    for (c='a';c<='z';c++) {        putchar(c);        putchar('\n');

}    return 0;

}说明:char 类型占用1字节,每个字符都映射对应一个整数。

查看字符对应整数#include int main() {    char c;    printf("=====小写====\n");    for (c='a';c<='z';c++) {        printf("%d\n",c);

}    printf("=====大写====\n");    for (c='A';c<='Z';c++) {        printf("%d\n",c);

}    return 0;

}大写字符和小写字符刚好差距32,  putchar('A'+32); 可转为小写。

2、字符串输出

puts:写字符串到标准输出

输出字符串示例#include int main() {    char string [] = "Hello world!";    puts(string);    return 0;

}

3、格式化输出

printf:打印格式化数据到标准输出,如果包含格式说明符(以%开头的子串)将格式化,用附加参数替换说明符(说明符可以认为是占位符)。

格式化时用到的说明符符号解释举例d 或者 i有符号十进制整数392

u无符号十进制整数7235

o无符号八进制610

x无符号十六进制整数7fa

X无符号十六进制整数(大写)7FA

f十进制浮点,小写392.65

F十进制浮点,大写392.65

e科学记数法(尾数/指数),小写3.9265e+2

c字符a

s字符串hello

p指针地址(内存地址)b8000000

%%%打印出一个%%

格式化输出示例#include int main() {    printf("字符:%c %c\n",'a',65);    printf("整数:%d %ld\n",600,6500000L);//%ld 长整

printf("浮点数:%f\n",33.3);    printf("十六进制:%x\n",0xffa);    printf("特殊打印:%%\n");    return 0;

}

结果字符:a A整数:600 6500000

浮点数:33.300000十六进制:ffa特殊打印:%

4、输入字符和字符串

getchar:从标准输入中获取字符

获取字符示例#include int main() {    uint8_t c;    puts("输入文本,在一个句子中包含.以结束:");    do{

c=getchar();        putchar(c);

}while (c!='.');    return 0;

}uint8_t c; uint8_t 大小与char一样

gets:从标准输入中获取字符串

获取字符串示例#include int main() {    char str[256];    puts("输入你的名字:");

gets(str);    printf("你的名字:%s\n",str);    return 0;

}

5、格式化输入

scanf:从标准输入中读取格式化数据,格式化说明符可参照 printf

格式化输入示例#include int main() {    char ch;    int num;    char str[10];    puts("输入一个字符:");    scanf("%c",&ch);    printf("用户的输入字符为:%c\n",ch);    puts("输入一个整数:");    scanf("%d",&num);    printf("用户输入的整数为:%d\n",num);    puts("输入字符串:");    scanf("%s",str);    puts(str);    return 0;

}int、char 等类型需要用&符号取得变量内存地址,变量 str 是一个数组,本身存储的就是内存地址,所以不用加上&符号。(可以理解为值与引用)

四、数组

1、一维数组

创建数组方式1:const int NUMS_LEN=10;int nums[NUMS_LEN];数组中元素的内存地址没有做过任何处理,有可能被之前其他程序使用过,所以数组中的默认的值是不可预期的。

演示数组中元素默认值:#include int main() {    const int NUMS_LEN=10;    int nums[NUMS_LEN];    for (int i = 0; i 

}    return 0;

}

创建数组方式2:int ages[]={19,20,30};

2、二维数组

创建方式1:int nums[3][4];for (int i = 0; i 

}

}

创建方式2:int nums[2][3]={

{1,2,3},

{4,5,6}

};二维数组直接初始化值需要指定长度!如果想对数组中的元素清0,可以在遍历中为元素赋值为0.

3、字符数组(字符串)

声明字符串并检查长度:char str[10];printf("长度:%ld\n",strlen(str));strlen 函数用于检测字符数组中字符的长度

存入字符串并检查长度:char str[10]="hello";printf("长度:%ld\n",strlen(str));

\0作为字符串结尾:char str[10]="he\0llo";printf("长度:%ld\n",strlen(str));字符串中不论内容多少,只要遇到 \0 就认为字符串结束!

char数组填充函数 memset:

memset(要填充的数组,要填充的值,要填充多长)#include #include int main() {    char str[]="你好";    memset(str,1,6);    for (int i = 0; i 

}    return 0;

}

关于中文:char str[2]="你好";printf("长度:%ld\n",strlen(str));//一个汉字占用3字节

五、字符串操作

1、字符串连接

strcat:连接字符串,将源字符串的副本附加到目标字符串。#include #include int main() {    char * str="hello";//要拼接的字符

char result[100];//目标字符

memset(result,0,100);//填充0到目标字符

strcat(result,str);//拼接str到result

strcat(result,"world");//拼接 world 到result

puts(result);    return 0;

}

strncat:连接指定数量的字符到目标字符串#include #include int main() {    char dist[10];    strncat(dist,"hello",3);    puts(dist);    return 0;

}

结果hel

2、格式化字符串

sprintf:将格式化数据写入字符串(格式方式和其他格式化方法很像)#include #include int main() {    char str[10];    memset(str,0,10);    int len,a=10,b=5;

len=sprintf(str,"%d+%d=%d",a,b,a+b);    printf("格式结果:[%s],长度为:%d",str,len);    return 0;

}

结果:格式结果:[10+5=15],长度为:7

3、字符串与基础数据类型转换

sscanf:从字符串中读取格式化数据

使用 sscanf 截取数据#include #include int main() {    //原字符串

char sentence[]="Java is 23 years old";    //保存拆分出来的数据的变量

int age;    char name[10];    sscanf(sentence,"%s %*s %d",name,&age);    printf("age is %d,name is %s",age,name);    return 0;

}"%s %*s %d" 分别表示了 Java is 23 (空格也包含在内),%*s 表示匹配的字符串但忽略该数据(可以理解占了个位置)。&age 这里需要将基本类型的内存地址引入。

使用 sscanf 转换数据类型#include int main() {    char * str="100";    int a;    sscanf(str,"%d",&a);    printf("转换后:%d",a);    return 0;

}

使用 atof 将字符串转为 double#include #include int main() {    double result=atof("3.14");    printf("转换后:%f",result);    return 0;

}

4、字符串比较

== 用来比较两个变量的内存地址,不能比较字符串的值。使用 strcmp 比较两个字符串的值,两个字符串的值相等返回 0。#include #include int main() {    char * str1="hello";    char str2[]="hello";    if(strcmp(str1,str2)==0){        puts("两个字符串的值相等");

}else{        puts("两个字符串的值不相等");

}    return 0;

}

5、字符串的截取

strchr:从指定字符开始截取#include #include int main() {    char * str="helloworld";    char * result=strchr(str,'w');    puts(result);    return 0;

}

strrchr:从最后一个指定字符开始截取#include #include int main() {    char * str="helloworld";    char * result=strrchr(str,'l');    puts(result);    return 0;

}

strstr:从指定字符串开始截取#include #include int main() {    char * str="helloworld";    char * result=strstr(str,"wo");    puts(result);    return 0;

}区分大小写

strncpy:从字符串中复制指定长度字符#include #include int main() {    char * str="helloworld";    char dest[10];    strncpy(dest,str,5);    puts(dest);    return 0;

}

使用指针从指定位置开始截取#include #include int main() {    char * str="helloworld";    char * str1=str+5;    puts(str1);    return 0;

}可以先利用指针操作从某个位置开始截取,然后利用 strncpy 截取指定个。

六、函数

声明和调用的方式和java很相似

1、main 函数的参数

main 函数的参数,也是程序运行时的参数

声明时需指定:1.参数的长度,2.参数数组#include int main(int argc,char ** argv) {    printf("参数的个数:%d\n",argc);    for (int i = 0; i 

}    return 0;

}

2、可变参数#include #include void testarg(int n,...){    printf("参数的个数:%d\n",n);

va_list args;

va_start(args,n);    for (int i = 0; i 

}

va_end(args);

}int main(int argc,char ** argv) {

testarg(2,10,55);    return 0;

}函数设置可变参数时需指定参数个数形参 int n ,和 ...(任意个数的参数)。需引入头文件 stdarg.h,va_list 类型保存有关变量参数的信息,va_start 初始化变量参数列表,va_arg 取出参数的值,va_end 结束使用变量参数列表

七、预处理

1、预设常量

除了可以用 #define 定义一个常量,还可以在编译参数中指定预设常量的值

编写没有声明常量但使用了常量的代码#include int main() {    printf("The num is %d\n",THE_NUM);    return 0;

}

使用命令进行编译和运行gcc -o test main.c -DTHE_NUM=4

test.exe-o 参数指定编译后可执行文件的文件名,-D 参数后面直接跟常量名和值(没有空格)

2、编译条件针对不同平台编译

1.编写代码#include #define WIN 1#define LINUX 2#define MAC 3int main() {#if PLATFORM==WIN

printf("Hello Windows\n");#elif PLATFORM==LINUX

printf("Hello Linux\n");#elif PLATFORM==MAC

printf("Hello MAC\n");#else

printf("Unknow platform\n");#endif

return 0;

}if、#elif、#else、#endif 这些都是编译条件,用于决定代码块是否编译

2.编译时指定条件//编译源码gcc -o test main.c -DPLATFORM=1//运行test.exe

3、头文件重复引入

1、演示重复引入

1.创建a.h#include "b.h"

2.创建b.h#include "a.h"

3.引入a.h#include #include "a.h"int main() {    return 0;

}

2、防止头文件重复引入

修改a.h#ifndef A_H#define A_H#include "b.h"#endif

修改b.h#ifndef B_H#define B_H#include "a.h"#endif通过标记一个常量来判断是否重复引入,一旦拥有这个常量将不再引入

八、指针

声明一个变量后,系统会为这个变量分配内存空间,每个变量都有一个内存地址,相当于旅馆的房间号。

我们要获取变量中的值需要通过内存地址来找到对应的值,但是还有另一种情况是这个变量中存放的是另个一变量的内存地址。这就好像你通过房间号找到这个房间,发现在这个房间里面是另一个房间的房间号。

所以,一个变量的地址就成为该变量的指针。

声明指针并指向一个变量的地址#include int main() {    int *a,*b;    int i=10;

a=&i;

b=&i;    printf("a的值为:%d\n",*a);    printf("b的值为:%d\n",*b);

i=99;    printf("a的值为:%d\n",*a);    printf("b的值为:%d\n",*b);    return 0;

}C语言用*表示指针,为指针赋值时 & 取出变量的地址。(指针a和指针b指向同一个地址,修改i后指针中的也会改变,这个很类似Java和C#中的引用类型)

指针的大小#include int main() {    int *a;    printf("size is %ld\n", sizeof(a));    return 0;

}64位系统中为8字节,32位中为4字节

1、函数指针

有参无返回值的函数指针#include void hello(int a,char* c){    printf("hello\n");

}int main() {    void(*fp)(int,char*)=&hello;

fp(1,"");    return 0;

}

有参有返回值的函数指针#include int test(int a){    printf("hello:%d\n",a);    return a;

}int main() {    int(*fp1)(int)=&test;    int result=fp1(11);    printf("返回值:%d\n",result);    return 0;

}

给函数指针设定类型别名#include void hello(){    printf("Hello\n");

}typedef void(*SimpleHello)();int main() {

SimpleHello h1=&hello;

h1();

SimpleHello h2=&hello;

h2();    return 0;

}重复定义时可以简化代码

2、无类型指针

无类型指针可以代表所有类型的数据

无类型指针存放字符串#include int main() {    void *test="Hello";    printf("%s\n",test);    return 0;

}

九、结构体与共同体

1、结构体

主要用结构体描述属性

定义使用结构体#include struct File{

char* name;    int size;

};int main() {    struct File file;

file.name="a.txt";

file.size=10;    printf("文件 %s 的大小为 %d\n",file.name,file.size);    struct File file1={"a.jpg",100};    printf("文件 %s 的大小为 %d\n",file1.name,file1.size);    return 0;

}结构体也可以像数组那样初始化(C#中也有结构,两者比较像可以对比记忆)

定义结构体类型简化代码#include typedef struct _File{

char* name;    int size;

}File;int main() {

File file;

file.name="a.txt";

file.size=10;    printf("文件 %s 的大小为 %d\n",file.name,file.size);

File file1={"a.jpg",100};    printf("文件 %s 的大小为 %d\n",file1.name,file1.size);    return 0;

}

2、结构体的内存对齐

结构体所占大小如何计算的?结构的大小由各变量与字节最大变量对齐后相加得出。

AAffA0nNPuCLAAAAAElFTkSuQmCC

结构体内存对齐

如图所示,三种情况:

1.当定义第一个变量大小为1字节,第二个变量比第一个变量大时,第一个变量要对齐大的变量,第一个变量填充为2字节,结构体大小为4字节。

2.前两变量加起来不足对齐第三个变量的大小,所以填充2字节对齐,结构体大小为8字节。

3.前4个变量加起来刚好对齐第5个变量的大小,无须对齐。最后一个变量没有对齐则填充2个字节对齐第5个变量,所以结构体大小为12字节。#include typedef struct _Data{

uint8_t a;//1

uint8_t b;//1

uint8_t c;//1

uint8_t d;//1

uint32_t e;//4

uint8_t f;//1}Data;int main() {    printf("size is %d\n", sizeof(Data));    return 0;

}此时结果为12

3、结构体指针

没有使用指针前#include typedef struct _Dog{

char * color;    int age;

}Dog;int main() {

Dog dog1={"红色",2};

Dog dog2=dog1;

dog1.age=3;    printf("(dog1 color is %s,age is %d),(dog2 color is %s,age is %d)\n"

,dog1.color,dog1.age,dog2.color,dog2.age

);    return 0;

}没有使用之前将dog1赋值给dog2相当于复制一个副本

使用结构体指针#include typedef struct _Dog {

char *color;    int age;

} Dog;int main() {

Dog dog1 = {"红色", 2};

Dog *dog2 = &dog1;

dog1.age = 3;    printf("(dog1 color is %s,age is %d),(dog2 color is %s,age is %d)\n",

dog1.color, dog1.age, dog2->color, dog2->age);    return 0;

}指针操作用法和之前一样,需要注意的地方是:结构体指针,获取结构体的值时需要使用 -> ,否则将编译错误

通过函数创建和销毁结构体指针#include #include typedef struct _Dog {

char *color;    int age;

} Dog;Dog* createDog(char* color,int age){

Dog* dog=malloc(sizeof(Dog));

dog->color=color;

dog->age=age;    return dog;

}void deleteDog(Dog* dog){    free(dog);

}int main() {

Dog* dog1=createDog("红色",3);    printf("(dog1 color is %s,age is %d)\n",

dog1->color, dog1->age);

deleteDog(dog1);    return 0;

}malloc函数分配内存,使用完毕后用free函数释放内存(释放后的内存的值不可预期何时修改,free函数调用后别的程序就可以使用这块空间了)

3、共同体

共同体的特点:共同体中声明的所有变量共用一块空间

声明及使用共同体#include typedef union _BaseData{    char ch;    uint8_t ch_num;

}BaseData;int main() {

BaseData data;

data.ch='A';    printf("ch_num is %d size is %d\n",data.ch_num, sizeof(BaseData));    return 0;

}变量 ch_num 和 ch 共用同一内存地址,大小为 1,共同体做类型转换比较方便。

实现颜色的操作#include //定义颜色结构体typedef struct _ColorARGB{

uint8_t blue;    uint8_t green;    uint8_t red;    uint8_t alpha;

}ColorARGB;//定义颜色共同体typedef union _Color{    uint32_t color;

ColorARGB colorARGB;

}Color;int main() {

Color c;

c.color=0xFFAADD00;    printf("red:%X",c.colorARGB.red);    return 0;

}存入的数据是以小端模式,所以定义颜色结构体时的通道的顺序和赋值的颜色顺序相反。结合结构体与共同体实现(巧妙)

十、文件操作

fopen函数:以指定文件名和模式获取一个流的FILE指针。

支持的模式模式说明"r"读:文件必须存在

"w"写:创建一个文件,如果已经存在则覆盖

"a"追加:向文件末尾追加内容,如果文件不存在则创建该文件

"r+"可做读取和修改的操作,文件必须存在

写文件//创建文件指针FILE * file=fopen("a.txt","w");if (file){    //写入内容

fputs("HelloWorld",file);    //关闭

fclose(file);

}else{    puts("文件操作失败!");

}

读文件#include int main() {

FILE * file=fopen("a.txt","r");    if (file){        char ch;        while(1){

ch=fgetc(file);            if(ch!=EOF){                printf("%c\n",ch);

}else{                break;

}

}

fclose(file);

}    return 0;

}

作者:享智同行

链接:https://www.jianshu.com/p/63234193e729

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
C语言入门到精通》是一本针对C语言学习的教程。本书以系统完整的方式介绍了C语言的基本概念、语法和应用,并通过大量的示例和练习帮助读者快速掌握C语言编程技巧。 书籍的第一部分主要介绍了C语言的基础知识。首先,它介绍了C语言的发展历程以及与其他编程语言的区别。然后,书中详细解释了C语言的数据类型、运算符、流程控制语句和函数等基本概念,帮助读者建立起对C语言编程的基础理论知识。 第二部分是关于C语言的高级应用和技巧。本书详细介绍了C语言的数组、指针、结构体和文件操作等高级特性。读者可以通过学习这些知识,掌握更加灵活、高效的编程方法,提高自己的程序设计能力。 此外,本书还包含了一些常用的C语言库函数和相关工具的介绍,如字符处理函数、内存管理函数和调试工具等。这些内容帮助读者更好地理解和使用C语言的相关资源,提高自己的编程效率。 《C语言入门到精通》不仅提供了理论知识的讲解,还提供了大量的实战编程示例和练习题。这些示例和练习题既可以帮助读者巩固所学知识,又可以提供编程实践的机会,培养读者的编程思维和解决问题的能力。 总的来说,这本书适合初学者作为C语言学习的入门教材,也适合有一定编程基础的读者作为C语言进阶学习的参考书。无论是新手还是专业人士,通过学习这本书,都可以逐步掌握C语言的基本概念和高级应用,从入门到精通。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值