本篇博客主要是向大家初步介绍一下C语言的基础内容,并没有深入地去探究,只是让大家对c语言有一个初步的认识,为后期深入学习c语言打基础。由于作者本人也是一名初学者,因此难免会有错误的地方,希望读者谅解,能够指出我的错误。另外,由于c语言内容较多,所以分成两篇,希望这篇博客能对大家有所帮助。
初步了解c语言的基础知识,对c语言有一个大概的认识。
C语言是一门通用计算机编程语言,广泛应用于底层开发。其实C并非初创的语言,其前身为B。它诞生于大名鼎鼎的贝尔实验室,一名叫KEN THOMPSON的技术人员用B发明游戏却玩不了->自己发明UNIX来玩->同事D.M.Ritchie也想玩->两人发明了C。当然作者发明的动机就是:改进B来玩游戏……二十世纪八十年代,为了避免各开发厂商用的C语言语法产生差异,由美国国家标准局为C语言制定了一套完整的美国国家标准语法,称为ANSI C,作为C语言最初的标准。 C语言是一门面向过程的计算机编程语言,与C++,Java等面向对象的编程语言有所不同。其编译器主要有Clang、GCC、WIN-TC、SUBLIME、MSVC、Turbo C等。
#include //stdio.h称为头文件 包含头文件
//h=head,std=stdandard,i=input,o=output 标准输入输出函数
int main()//main函数是程序的入口,main函数有且仅有一个
{
printf("Hello world\n");
//c的输入输出函数printf()的作用是输出一个字符串
//printf是c语言提供给我们的库函数,调用它,需要包含头文件
return 0;// 返回一个整数0
}
在程序的指导下,计算机可以做很多事,例如,数值计算,数据排序,拨打电话等等,要完成这些事情,程序需要使用数据,即承载数据的信息和字符,而这些数据有不同的类型。用生活中的事来举例。
人的姓名*** - 字符串
物品的价格23.5¥ - 浮点型
操场的长度400m - 整形
数据类型符号 | 数据类型 | 输出格式 | 字节 |
---|---|---|---|
char | 字符型 | %c | 1 |
short(int ) | 短整型 | %d | 2 |
int | 整形 | %d | 4 |
long(int) | 长整型 | %d | 4 |
long long | 长长整形 | %d | 8 |
float | 单精度浮点型 | %f | 4 |
double | 双精度浮点型 | %lf | 8 |
long double | 长双精度浮点型 | %llf | 8 |
注意:sizeof是用来计算数据类型所占字节数的操作符
字节是什么呢?首先,计算机的所有指令和数据都是存在计算机的存储部件——内存中,内存中的存储单元是一个线性地址表,按字节进行编址,即每个字节的内存单元中都对应着一个唯一的地址。
有一些注意的地方,希望大家看一下(别问我为什么不敲,问就是懒)
我们可以观察到生活中有些值是不变的,比如圆周率,性别,身份证号,血型等等;而有些值是可以改变的,例如,人的身高,体重,年龄等等。对于不变的值,c语言用常量来表达,可变的数值,c语言用变量来表达。
#include
int main()
{
int age = 18;
float height = 1.75;
char ch = "w";
return 0;
}
#include
int age = 20;//全局变量
int main()
{
int age = 18;//局部变量
float height = 1.75;//局部变量
printf("age = %d\n",age);//18
return 0;
}
总结:上面的局部变量的定义其实没有什么问题,当局部变量和全局变量同名时,局部变量优先使用。
#include
int main()
{
int num1 = 0;//开辟一块内存空间
int num2 = 0;
int sum = 0;
printf("输入两个操作数:>");
scanf("%d %d", &num1, &num2);//scanf是c语言的标准输入函数
//代表输入两个整数,&为取地址操作符,将输入的数据存入num1,num2的内存空间
sum = num1 + num2;
printf("sum = %d\n", sum);
return 0;
}
这里可能会遇到如下问题:
解决方法请点击下面的链接
https://editor.csdn.net/md/?articleId=124087600
int main()
{
{
int a = 0;
a = 12;
printf("%d\n", a);
}
printf("%d\n", a);//报错:a是未定义的标识符
//a只在他所在的作用域{}中有效,一旦出{},a的内存空间就被释放
return 0;
}
int main()
{
int a = 0;
{
a = 12;
printf("%d\n", a);
}
printf("%d\n", a);//正常
return 0;
}
这里有一个特殊情况
a如果在别的源文件中定义,我们同样也可以使用,不过需要声明是来自外部的符号,用extern关键字来声明。
综上结论如下:
作用域
作用域(scope)是程序设计概念,通常来说,一段程序代码中所用到的名字并不总是有效/可用的。而限定这个名字的可用性的代码范围就是这个名字的作用域。
C语言中的常量和变量的定义的形式有所差异。
C语言中的常量分为以下以下几种:
#include
//举例
enum Sex
{
MALE,
FEMALE,
SECRET
};
//括号中的MALE,FEMALE,SECRET是枚举常量
int main()
{
//字面常量演示
6.66;//字面常量
1000;//字面常量
//const 修饰的常变量
const float x = 4.4f; //这里的x是const修饰的常变量
x = 5.4;//是不能直接修改的!
//#define的标识符常量 演示
#define MAX 100
printf("max = %d\n", MAX);
//枚举常量演示
printf("%d\n", MALE);//0
printf("%d\n", FEMALE);//1
printf("%d\n", SECRET);//2
return 0;
}
//注:枚举常量的默认是从0开始,依次向下递增1的
注意:
上面例子上的 x被称为 const 修饰的常变量, const 修饰的常变量在C语言中只是在语法层面限制了变量 x 不能直接被改变,但是 x本质上还是一个变量的,所以叫常变量。
"Hello world!\n"
这种由双引号(Double Quote)引起来的一串字符称为字符串字面值(String Literal),或者简称字符串。
注意:字符串的结束标志是一个 \0 的转义字符。在计算字符串长度的时候 \0 是结束标志,不算作字符串内容。
arr1是以字符串来初始化,而字符串的结束标志为’\0’,所以我们在定义字符串时,系统默认末尾会添加一个’\0’(隐藏起来了),而arr2是以单个字符来初始化的,系统不会默认添加’\0’。但是有些小伙伴就会有疑问了,为啥arr2的输出有问题。我们继续往下康康。
首先我们需要了解数组在内存中存储的方式
我们把字符串存入内存中,但是内存是非常大的,内存给arr1分配了一块空间,给arr2分配了一块空间。而在它附近有很多的内存空间,里面存有一些数据,上面讲到’\0’是字符串结束的标志,所以arr1打印完就停止了,但是arr2没有规定字符串长度,也没有’\0’,所以他会继续往附近的内存访问,直到遇到’\0’才会停止访问。
看上面的图片,因为没有’\0’,arr2会继续访问附近的内存,知道访问到有’\0’的内存,所以arr2的长度远远大于arr1。
我们再看一段代码:
include <stdio.h>
//下面代码,打印结果是什么?为什么?(突出'\0'的重要性)
int main()
{
char arr1[] = "bit";
char arr2[] = {'b', 'i', 't'};
char arr3[] = {'b', 'i', 't', '\0'};
char arr4[3] = {'b','i','t'};
char arr5[4] = {'b','i','t'};
char arr6[7] = {'h','e','l','l','o'};
char arr7[3] = {'h','e','l','l','o'};
printf("%s\n", arr1);
printf("%s\n", arr2);
printf("%s\n", arr3);
printf("%s\n", arr4);
printf("%s\n", arr5);
printf("%s\n", arr6);
printf("%s\n", arr7);
return 0;
}
另外,对于数组初始化的下标问题(下标就是arr[]中的数字)也要注意,初始化时,如果数组下标小于字符个数,编译器会直接报错,如arr7。初始化时,注意’\0’也是字符,如果不把’\0’算上,如arr4,arr4会像arr3一样,继续访问,直到遇到’\0’。如果初始化时,数组下标超过了(字符个数+’\0’),则编译器默认其余元素为’\0’。大家应该明白了吧。
加入我们要在屏幕上打印一个目录: c:\code\test\245.c
我们该如何写代码?
#include
int main()
{
printf("c:\code\test\245.c\n");
return 0;
}
实际上程序运行的结果是这样的:
这里就不得不提一下转义字符了。转义字符顾名思义就是转变意思。
下面看一些转义字符。
转义字符 | 释义 |
---|---|
\? | 在书写连续多个问号时使用,防止他们被解析成三字母词 |
\’ | 用于表示字符常量’ |
\’’ | 用于表示一个字符串内部的双引号 |
\\ | 用于表示一个反斜杠,防止他被解析成一个转义字符 |
\a | 警告字符,蜂鸣 |
\b | 退格符 |
\f | 进纸符 |
\n | 换行符 |
\r | 回车符 |
\t | 水平制表符 |
\v | 垂直制表符 |
\ddd | 用于表示1~3个8进制数字 如:\130 |
\xdd | 用于表示2个16进制数字 如:\x30 |
前面的大家认识一下就行了,现在着重讲解一下后两个。
八进制130转十进制:
18² + 38¹ + 08º = 64 + 22 + 0 = 88
十六进制x30转十进制 :
016º+ 3*16¹ = 48+ 0 = 48
int main()
{
printf("%c\n",'\130');
printf("%c\n",'\x30');
return 0;
这段代码的意思是八进制数130转成十进制数88所代表的字符,十六进制x30转十进制数48所代表的字符。由于计算机只能识别二进制的指令,所以数据是以二进制的补码存储在内存中的。所以早期的科学家想出了一个办法,用二进制数代替字符。及字符本质上也是一个数字,每个字符都有唯一一个与之对应的整数。不同编号代表不同的字符,这种编号就叫做ASCII编码。
ASCII编码表:
//程序输出什么?
#include
int main()
{
printf("%d\n", strlen("abcdef"));//6
// strlen是c语言的库函数,作用是计算字符的个数(不算'\0'欧)
//所以上面打印的结果是6
//请大家看一下,下面这个会打印什么结果,答案放到结尾
printf("%d\n", strlen("c:\test\628\test.c"));
return 0;
}
/*
typedef 类型定义 ,类型重命名
typedef unsigned int u_int;
*/
int main()
{
typedef unsigned int num = 100;
u_int num2 = 100;
return 0;
}
int main()
{
int a = 10;//%p用来打印地址
printf("%p\n",&a);
int* pa = &a;//pa用来存放地址,在c语言中叫指针变量
//*说明pa是指针变量
char ch = 'w';
char* pc = &ch;
return 0;
}
注释有两种风格:
如果你好好学习,校招时拿一个好offer,走上人生巅峰。
如果你不学习,毕业等于失业,回家种地。
这就是选择!
int main()
{
int coding = 0;
printf("你会去敲代码吗?(选择1 or 0):>");
scanf("%d", &coding);
if(coding == 1)
{
prinf("坚持,你会有好offer\n");
}
else
{
printf("放弃,回家种地\n");
}
return 0;
}
有些事必须一直做,比如大家要吃饭睡觉,比如大家日复一日的学习,才能有好offer。
还比如:
C语言中如何实现循环呢?
while语句-讲解
for语句(后期讲)
do … while语句(后期讲)
//while循环的实例
#include
int main()
{
printf("好好学习计算机和编程\n");
int line = 0;
while(line <= 100000)//不满足条件,就一直进入循环
{
line++;
printf("我要继续努力敲代码\n");
}
//if(line > 100000)可有可无
printf("好offer\n");//满足条件跳出循环
return 0;
}
注意:一定要有跳出循环的条件,并且随着程序的执行,不断地接近跳出的条件,不能让程序陷入死循环。
#include
int main()
{
int a = 0;
int b = 0;
int max = 0;
if(a > b)
max = a;
else
max = b;
printf("max = %d\n",max);
return 0;
}
//函数形式如下:
#include
//int—函数返回类型 get_max-函数名 int x,int y-函数参数
//定义函数
int get_max(int x, int y)//形式参数
{
int z;
if (x < y)
z = y;
else
z = x;
return z;
}
int main()
{
int a = 10;
int b = 20;
//调用函数
int max = get_max(a, b);//实际参数
printf("max = %d\n",max);
return 0;
}
我们来分析一下函数的调用过程,我们输入a和b的值,通过调用函数,把值传递给形式参数,然后函数返回一个值,再赋值给max,然后打印它。
`
通过调用函数,可以简化代码。
让我看看有没有人把\628当作八进制的,注意八进制没有8,只有0~7,十六进制也没有16,只有0 ~15,注意是0 1 2 3 4 5 6 7 8 9 A B C D E F(10=A,11=B,12=C,13=D,14=E,15=F)。但是\62仍然是八进制数,第三位是隐藏的’\0’,所以’\62’是一个转义字符。
首先恭喜大家选择学习c语言,俗话说,c生万物,他甚至是其他c语言的母语,比如Java就是c语言编写的,怎么样,厉害吧,并且几乎所有的操作系统都是用c语言编写的,例如windows(真牛逼)。由于c语言是一个面向过成的语言,所以他会面向程序执行流程思考,有助于我们深入了解计算机的低层开发,说这么多,就是想表达c语言很好,希望大家能坚持下去,不断学习,俗话说,行百里者半九十,坚持下去,会有意想不到的惊喜。