C语言基础知识(一)-字节、变量、常量、数据类型以及进制

简介: 本文是C语言的基础知识,主要讲解字节、变量、常量、数据类型以及不同进制。

  本文是C语言的基础知识,主要讲解字节、变量、常量、数据类型以及不同 进制


字节


什么是字节


       字节是存储数据的基本单位,并且是硬件所能访问的最小单位。


       内存中存储数据的最小单位是"位"。字节是存储数据的基本单位,位是存储数据的最小单位,不要混淆了。


什么是位


       计算机要处理的数据(诸如数字、文字、符号、图形、音频、视频等)是以二进制的形式存放在内存中的;硬件通过地址总线访问内存的,而地址是以字节为单位进行分配的,所以地址总线只能精确到字节,所以将字节作为最小的可操作单元,8个比特(Bit)称为一个字节(Byte)。


字节换算


       存储单位主要有bit(位)、B(字节)、KB(千字节)、MB(兆字节)、GB(千兆字节)、TB(太字节)、PB(拍字节)、EB(艾子节)。它们之间主要有如下换算关系:


1B=8bit;1KB=1024B;1MB=1024KB;1GB=1024MB; 1TB=1024GB;1PB=1024TB;1EB=1024PB。


       其中B是Byte的缩写,TB(太字节)、PB(拍字节)、EB(艾子节)用的比较少。


       例如计算机的内存是8GB,那么它能存放多少个0或1(即能存放多少位)呢?        


       8×1024×1024×1024×8位。


进制


微信图片_20220520152426.png

       进制是学习计算机语言最基本的知识,所以一定要掌握。进制就是逢几进一,r进制就是逢r进一。计算机只能识别二进制,计算机中的数据只有0和1,逢二进一,就是二进制。人类最习惯使用的是十进制,而为了实际需要,又建立了八进制和十六进制。八进制就是逢八进一,十六进制就是逢十六进一。


       C语言中可以使用的进制有二进制、八进制、十进制、十六进制。


二进制


       二进制由0和1两个数字组成,使用时必须以0b或0B(不区分大小写)开头,例如:


int a = 0b110;  //换算成十进制为 6=(0x1+1x2+1x4)
int b = 0b110110;  //换算成十进制为 54=(0x1+1x2+1x4+0x8+1x16+1x32)
int c = -0B100001;  //换算成十进制为 -33=-(1x1+...+1x32)


注意: 标准的C语言并不支持上面的二进制写法,只是有些编译器自己进行了扩展,才支持二进制数字。


八进制


       八进制由0~7八个数字组成,使用时必须以0开头(注意是数字 0,不是字母o),例如:


int a = 013;  //换算成十进制为 11=(3x1+1x8)
int b = 0101;  //换算成十进制为 65=(1x1+0x8+1x64)
int c = -0177777;  //换算成十进制为 -65535=(7x1+7x8+7x64+7x512+7x4096+1x32768)


十六进制


       十六进制由数字0~9、字母A~F 或 a~f(不区分大小写)组成,使用时必须以0x或0X(不区分大小写)开头,例如:


int a = 0X2A;  //换算成十进制为 42=(10x1+2x16)
int b = -0XA0;  //换算成十进制为 -160=(0x1+10x16)
int c = 0xffff;  //换算成十进制为 65535=(15x16x0+15x16+15x16x16+15x16x16x16)


十进制


       十进制由0~9 十个数字组成,没有任何前缀,和我们平时的书写格式一样。


进制转换


       上面讲了r进制转十进制。可以说十进制是任意进制间相互转换的桥梁,任何进制都可以先转换成十进制,然后再转换成需要的进制。


进制数的输出


       C语言中常用的整数有 short、int 和 long 三种类型,通过 printf 函数,可以将它们以八进制、十进制和十六进制的形式输出。


微信图片_20220520152723.png


       八进制数字和十进制数字不区分大小写,所以格式控制符都用小写形式(有些编译器不支持大写可能会报错)。


十六进制数字的表示用到了英文字母,有大小写之分,要在格式控制符中体现出来:


  • %hx、%x 和 %lx 中的x小写,表明以小写字母的形式输出十六进制数;


  • %hX、%X 和 %lX 中的X大写,表明以大写字母的形式输出十六进制数。 以不同进制的形式输出整数,例:


#include <stdio.h>
int main()
{
    short a = 0b110110;  //二进制数字
    int b = 0101;  //八进制数字
    long c = 0xffff;  //十六进制数字
    printf("a=%ho, b=%o, c=%lo\n", a, b, c);  //以八进制形似输出
    printf("a=%hd, b=%d, c=%ld\n", a, b, c);  //以十进制形式输出
    printf("a=%hx, b=%x, c=%lx\n", a, b, c);  //以十六进制形式输出(字母小写)
    printf("a=%hX, b=%X, c=%lX\n", a, b, c);  //以十六进制形式输出(字母大写)
    return 0;
}


运行结果:


a=66, b=101, c=177777
a=54, b=65, c=65535
a=36, b=41, c=ffff
a=36, b=41, c=FFFF


 从这个例子可以发现,一个数字不管以何种进制来表示,都能够以任意进制的形式输出。数字在内存中始终以二进制的形式存储,其它进制的数字在存储前都必须转换为二进制形式;同理,一个数字在输出时要进行逆向的转换,也就是从二进制转换为其他进制。


输出时加上前缀


       注意上面的例子,会发现有一点小瑕疵,如果只看输出结果:


       对于八进制数字,它没法和十进制、十六进制区分,因为八进制、十进制和十六进制都包含 0~7 这几个数字。


       对于十进制数字,它没法和十六进制区分,因为十六进制也包含 0~9 这几个数字。如果十进制数字中还不包含 8 和 9,那么也不能和八进制区分了。


       对于十六进制数字,如果没有包含 a~f 或者 A~F,那么就无法和十进制区分,如果还不包含 8 和 9,那么也不能和八进制区分了。


       区分不同进制数字的一个简单办法就是,在输出时带上特定的前缀。在格式控制符中加上#即可输出前缀,如%#x、%#o、%#lX、%#ho 等,例:


#include <stdio.h>
int main()
{
    short a = 0b110110;  //二进制数字
    int b = 0101;  //八进制数字
    long c = 0xffff;  //十六进制数字
   printf("a=%#ho, b=%#o, c=%#lo\n", a, b, c);  //以八进制形似输出
    printf("a=%hd, b=%d, c=%ld\n", a, b, c);  //以十进制形式输出
    printf("a=%#hx, b=%#x, c=%#lx\n", a, b, c);  //以十六进制形式输出(字母小写)
    printf("a=%#hX, b=%#X, c=%#lX\n", a, b, c);  //以十六进制形式输出(字母大写)出(字母大写)
    return 0;
}


运行结果:


a=066, b=0101, c=0177777
a=54, b=65, c=65535
a=0x36, b=0x41, c=0xffff
a=0X36, b=0X41, c=0XFFFF


十进制数字没有前缀,所以不用加#。如果你加上了,那么它的行为是未定义的,有的编译器支持十进制加#,只不过输出结果和没有加#一样,有的编译器不支持加#,可能会报错,也可能会导致奇怪的输出;但是,大部分编译器都能正常输出,不至于当成一种错误。


数据类型


       在 C 语言中,数据类型指的是用于声明不同类型的变量或函数的一个广泛的系统。变量的类型决定了变量存储占用的空间,以及如何解释存储的位模式。


       C语言基本数据类型:


微信图片_20220520153045.png


       整型数据类型的存储大小和值范围的细节:

微信图片_20220520153059.png


sizeof 操作符


       获取某个数据类型的长度可以使用 sizeof 操作符,例:


#include <stdio.h>
int main()
{
    short a = 10;
    int b = 100;
    int short_length = sizeof a;
    int int_length = sizeof(b);
    int long_length = sizeof(long);
    int char_length = sizeof(char);
    printf("short=%d, int=%d, long=%d, char=%d\n", short_length, int_length, long_length, char_length);
    return 0;
}


Win64 环境下的运行结果:


short=2, int=4, long=8, char=1


浮点类型占用的存储空间以及它的范围值,例:


#include <stdio.h>
#include <float.h>
int main()
{
   printf("float 存储最大字节数 : %lu \n", sizeof(float));
   printf("float 最小值: %E\n", FLT_MIN );
   printf("float 最大值: %E\n", FLT_MAX );
   return 0;
}


%E为以指数形式输出单、双精度实数 运行结果:


float 存储最大字节数 : 4 
float 最小值: 1.175494E-38
float 最大值: 3.402823E+38


变量


       变量其实只不过是程序可操作的存储区的名称。C 中每个变量都有特定的类型,类型决定了变量存储的大小和布局,该范围内的值都可以存储在内存中,运算符可应用于变量上。


变量命名规则:


  • 变量的名称可以由字母、数字和下划线字符组成。


  • 必须以字母或下划线开头。


  • 大写字母和小写字母是不同的,因为 C 是大小写敏感的。


  • 不能和保留字同名(关键字);


C中的变量定义


int a;


 int 是整数。a 是我们给这块区域起的名字;当然也可以叫其他名字,例如 scc、2016 等。

       注意:int 和 a 之间是有空格的,它们是两个词。最后的分号,int a表达了完整的意思,是一个语句,要用分号来结束。


C语言中这样向内存中放整数:


a=520;


    = 是一个新符号,它在数学中叫“等于号”,例如 1+2=3,但在C语言中,这个过程叫做赋值(Assign)。赋值是指把数据放到内存的过程

把上面的两个语句连起来:


int a;
a=520;


就520放到了一块叫做 a 的内存区域。你也可以写成一个语句:


int a=520;


   a 中的整数不是一成不变的,只要我们需要,随时可以更改。更改的方式就是再次赋值,例如:


int a=520;
a=1314;
a=6666;


  第二次赋值,会把第一次的数据覆盖(擦除)掉,也就是说,a 中最后的值是6666,1314、520已经不存在了,再也找不回来了。

       因为 a 的值可以改变,所以我们给它起了一个形象的名字,叫做变量(Variable)


int a;


     创造了一个变量 a,我们把这个过程叫做变量定义。a=520;把520交给了变量 a,我们把这个过程叫做给变量赋值;又因为是第一次赋值,也称变量的初始化,或者赋初值

       你可以先定义变量,再初始化,例如:


int scc;
scc=888;


 也可以在定义的同时进行初始化,例如:


int scc=888;


这两种方式是等价的。


连续定义多个变量


int a, b, c;
float m = 4.22, n = 77.75;
char p, q = 'c';


 连续定义的多个变量以逗号,分隔,并且要拥有相同的数据类型;变量可以初始化,也可以不初始化。


常量


       常量是固定值,在程序执行期间不会改变。这些固定的值,又叫做字面量


       常量可以是任何的基本数据类型,比如整数常量、浮点常量、字符常量,或字符串字面值,也有枚举常量。


       常量就像是常规的变量,只不过常量的值在定义后不能进行修改。


微信图片_20220520153745.png


整数常量


       整数常量可以是十进制、八进制或十六进制的常量。前缀指定基数:0x 或 0X 表示十六进制,0 表示八进制,不带前缀则默认表示十进制。


       整数常量也可以带一个后缀,后缀是 U 和 L 的组合,U 表示无符号整数(unsigned),L 表示长整数(long)。后缀可以是大写,也可以是小写,U 和 L 的顺序任意。


       下面列举几个整数常量的实例:


212         /* 合法的 */
215u        /* 合法的 */
0xFeeL      /* 合法的 */
078         /* 非法的:8 不是八进制的数字 */
032UU       /* 非法的:不能重复后缀 */


浮点常量


       浮点常量由整数部分、小数点、小数部分和指数部分组成。您可以使用小数形式或者指数形式来表示浮点常量。


       当使用小数形式表示时,必须包含整数部分、小数部分,或同时包含两者。当使用指数形式表示时, 必须包含小数点、指数,或同时包含两者。带符号的指数是用 e 或 E 引入的。


       下面列举几个浮点常量的实例:


3.14159       /* 合法的 */
314159E-5L    /* 合法的 */
510E          /* 非法的:不完整的指数 */
210f          /* 非法的:没有小数或指数 */
.e55          /* 非法的:缺少整数或分数 */


字符常量


       字符常量是括在单引号中,例如,'x' 可以存储在 char 类型的简单变量中。


       字符常量可以是一个普通的字符(例如 'x')、一个转义序列(例如 '\t'),或一个通用的字符(例如 '\u02C0')。


       在 C 中,有一些特定的字符,当它们前面有反斜杠时,它们就具有特殊的含义,被用来表示如换行符(\n)或制表符(\t)等。下面咱列出了一些这样的转义序列码:


微信图片_20220520153947.png


 咱们实践一下子,例:


#include <stdio.h>
int main()
{
   printf("Hello\t帅次\n\n");
   return 0;
}


运行结果:


Hello 帅次


字符串常量


       字符串字面值或常量是括在双引号 "" 中的。一个字符串包含类似于字符常量的字符:普通的字符、转义序列和通用的字符。


       您可以使用空格做分隔符,把一个很长的字符串常量进行分行。


       下面的实例显示了一些字符串常量。下面这三种形式所显示的字符串是相同的。

"hello, dear"
"hello, \
dear"
"hello, " "d" "ear"


定义常量


       在 C 中,有两种简单的定义常量的方式:


  • 使用 #define 预处理器。例:


#include <stdio.h>
#define a 40   
#define b 13
#define NEWLINE '\n'
int main()
{
   int scc;  
   scc = a * b;
   printf("value of scc : %d", scc);
   printf("%c", NEWLINE);
   return 0;
}


运行结果:


value of scc : 520


  • 使用 const 关键字。例:


#include <stdio.h>
int main()
{
   const int  a = 40;
   const int  b  = 13;
   const char NEWLINE = '\n';
   int scc;  
   scc = a * b;
   printf("value of scc : %d", scc);
   printf("%c", NEWLINE);
   return 0;
}


运行结果:


value of scc : 520


注意:把常量定义为大写字母形式,是一个很好的编程习惯。


如有错误,烦请斧正

相关文章
|
3月前
|
存储 程序员 编译器
C 语言中的数据类型转换:连接不同数据世界的桥梁
C语言中的数据类型转换是程序设计中不可或缺的一部分,它如同连接不同数据世界的桥梁,使得不同类型的变量之间能够互相传递和转换,确保了程序的灵活性与兼容性。通过强制类型转换或自动类型转换,C语言允许开发者在保证数据完整性的前提下,实现复杂的数据处理逻辑。
|
14天前
|
存储 人工智能 程序员
一文彻底搞清楚C语言的数据类型和变量
本文介绍了数据类型(基本、构造、指针、空类型)、变量(使用、命名规则、作用域)和常量(字面、符号、枚举、表达式),帮助初学者理解编程基础概念。坚持学习,定能创造奇迹!
162 1
一文彻底搞清楚C语言的数据类型和变量
|
2月前
|
C语言
【C语言程序设计——入门】基本数据类型与表达式(头歌实践教学平台习题)【合集】
这份文档详细介绍了编程任务的多个关卡,涵盖C语言的基础知识和应用。主要内容包括: 1. **目录**:列出所有关卡,如`print函数操作`、`转义字符使用`、`数的向上取整`等。 2. **各关卡的任务描述**:明确每关的具体编程任务,例如使用`printf`函数输出特定字符串、实现向上取整功能等。 3. **相关知识**:提供完成任务所需的背景知识,如格式化输出、算术运算符、关系运算符等。 4. **编程要求**:给出具体的代码编写提示。 5. **测试说明**:包含预期输入输出,帮助验证程序正确性。 6. 文档通过逐步引导学习者掌握C语言的基本语法和常用函数,适合初学者练习编程技能。
72 1
|
3月前
|
存储 编译器 C语言
【C语言】C语言的变量和声明系统性讲解
在C语言中,声明和定义是两个关键概念,分别用于告知编译器变量或函数的存在(声明)和实际创建及分配内存(定义)。声明可以多次出现,而定义只能有一次。声明通常位于头文件中,定义则在源文件中。通过合理组织头文件和源文件,可以提高代码的模块化和可维护性。示例包括全局变量、局部变量、函数、结构体、联合体、数组、字符串、枚举和指针的声明与定义。
95 12
|
3月前
|
存储 算法 C语言
【C语言】字符常量详解
字符常量是C语言中处理字符数据的重要工具。通过单引号括起一个字符,我们可以方便地使用字符常量进行字符判断、字符运算和字符串处理等操作。理解字符常量的表示方法、使用场景和ASCII码对应关系,对于编写高效的C语言程序至关重要。
254 11
|
3月前
|
存储 编译器 C语言
【C语言】数据类型全解析:编程效率提升的秘诀
在C语言中,合理选择和使用数据类型是编程的关键。通过深入理解基本数据类型和派生数据类型,掌握类型限定符和扩展技巧,可以编写出高效、稳定、可维护的代码。无论是在普通应用还是嵌入式系统中,数据类型的合理使用都能显著提升程序的性能和可靠性。
88 8
|
3月前
|
安全 程序员 C语言
【C语言】指针的爱恨纠葛:常量指针vs指向常量的指针
在C语言中,“常量指针”和“指向常量的指针”是两个重要的指针概念。它们在控制指针的行为和数据的可修改性方面发挥着关键作用。理解这两个概念有助于编写更安全、有效的代码。本文将深入探讨这两个概念,包括定义、语法、实际应用、复杂示例、最佳实践以及常见问题。
75 7
|
3月前
|
C语言
【C语言】全局搜索变量却找不到定义?原来是因为宏!
使用条件编译和 `extern` 来管理全局变量的定义和声明是一种有效的技术,但应谨慎使用。在可能的情况下,应该优先考虑使用局部变量、函数参数和返回值、静态变量或者更高级的封装技术(如结构体和类)来减少全局变量的使用。
57 5
|
3月前
|
C语言
【C语言】<常量> 之群英荟萃
在C语言中,常量(Constants)是指在程序运行过程中其值不能被修改的固定值。常量包括数值常量(整型和浮点型)、字符常量、字符串常量、使用const关键字定义的常量变量以及枚举常量。
50 4
|
3月前
|
编译器 C语言
【C语言】常量的 “前缀和后缀” 大通关!
在C语言中,常量的前缀和后缀用于明确指定常量的类型和进制系统。前缀主要用于区分不同进制的数字常量,而后缀则用于区分不同类型的整数和浮点数。正确使用前缀和后缀,可以提高代码的可读性和可维护性,确保编译器正确地理解和处理常量。
107 1