文章目录
1. 概述
变量其实只不过是程序可操作的存储区的名称。
在 C++ 中,有多种变量类型可用于存储不同种类的数据。
C++ 中每个变量都有指定的类型,类型决定了变量存储的大小和布局,该范围内的值都可以存储在内存中,运算符可应用于变量上。
变量的名称可以由字母、数字和下划线字符组成。它必须以字母或下划线开头。
大写字母和小写字母是不同的,因为 C++ 是大小写敏感的。
类型 | 描述 |
---|---|
bool | 布尔类型,存储值 true 或 false,占用 1 个字节。 |
char | 字符类型,用于存储 ASCII 字符,通常占用 1 个字节。 |
int | 整数类型,通常用于存储普通整数,通常占用 4 个字节。 |
float | 单精度浮点值,用于存储单精度浮点数。单精度是这样的格式,1 位符号,8 位指数,23 位小数,通常占用4个字节。 |
double | 双精度浮点值,用于存储双精度浮点数。双精度是 1 位符号,11 位指数,52 位小数,通常占用 8 个字节。 |
void | 表示类型的缺失。 |
wchar_t | 宽字符类型,用于存储更大范围的字符,通常占用 2 个或 4 个字节。 |
C++ 也允许定义各种其他类型的变量,比如枚举、指针、数组、引用、数据结构、类等等
-
整数类型(Integer Types):
int
:用于表示整数,通常占用4个字节。short
:用于表示短整数,通常占用2个字节。long
:用于表示长整数,通常占用4个字节。long long
:用于表示更长的整数,通常占用8个字节。
数据类型 | 占用空间 | 取值范围 |
---|---|---|
short(短整型) | 2字节 | (-2^15 ~ 2^15-1) |
int(整型) | 4字节 | (-2^31 ~ 2^31-1) |
long(长整形) | Windows为4字节,Linux为4字节(32位),8字节(64位) | (-2^31 ~ 2^31-1) |
long long(长长整形) | 8字节 | (-2^63 ~ 2^63-1) |
-
浮点类型(Floating-Point Types):
float
:用于表示单精度浮点数,通常占用4个字节。double
:用于表示双精度浮点数,通常占用8个字节。long double
:用于表示更高精度的浮点数,占用字节数可以根据实现而变化。
数据类型 | 占用空间 | 有效数字范围 |
---|---|---|
float | 4字节 | 7位有效数字 |
double | 8字节 | 15~16位有效数字 |
-
字符类型(Character Types):
char
:用于表示字符,通常占用1个字节。wchar_t
:用于表示宽字符,通常占用2或4个字节。char16_t
:用于表示16位Unicode字符,占用2个字节。char32_t
:用于表示32位Unicode字符,占用4个字节。
-
布尔类型(Boolean Type):
bool
:用于表示布尔值,只能取true
或false
。
-
枚举类型(Enumeration Types):
enum
:用于定义一组命名的整数常量。
-
指针类型(Pointer Types):
type*
:用于表示指向类型为type
的对象的指针。
-
数组类型(Array Types):
type[]
或type[size]
:用于表示具有相同类型的元素组成的数组。
-
结构体类型(Structure Types):
struct
:用于定义包含多个不同类型成员的结构。
-
类类型(Class Types):
class
:用于定义具有属性和方法的自定义类型。
-
共用体类型(Union Types):
union
:用于定义一种特殊的数据类型,它可以在相同的内存位置存储不同的数据类型。
在 C++ 中,类型的长度(即占用的字节数)取决于编译器和计算机架构,然而,C++ 标准规定了不同整数类型的最小范围,而不是具体的字节数,这是为了确保代码在不同的系统上都能正确运行。
请注意,以上类型的范围只是 C++ 标准规定的最小要求,实际上,许多系统上这些类型可能占用更多的字节,例如,很多现代计算机上 int 通常占用 4 字节,而 long 可能占用 8 字节。
2. 变量定义
变量定义就是告诉编译器在何处创建变量的存储,以及如何创建变量的存储。
变量定义指定一个数据类型,并包含了该类型的一个或多个变量的列表,如下所示:
type variable_list;
在这里,type 必须是一个有效的 C++ 数据类型,可以是 char、wchar_t、int、float、double、bool 或任何用户自定义的对象,variable_list 可以由一个或多个标识符名称组成,多个标识符之间用逗号分隔。下面列出几个有效的声明:
int i, j, k;
char c, ch;
float f, salary;
double d;
行 int i, j, k; 声明并定义了变量 i、j 和 k,这指示编译器创建类型为 int 的名为 i、j、k 的变量。
变量可以在声明的时候被初始化(指定一个初始值)。初始化器由一个等号,后跟一个常量表达式组成,如下所示:
type variable_name = value;
示例:
extern int d = 3, f = 5; // d 和 f 的声明
int d = 3, f = 5; // 定义并初始化 d 和 f
byte z = 22; // 定义并初始化 z
char x = 'x'; // 变量 x 的值为 'x'
不带初始化的定义:带有静态存储持续时间的变量会被隐式初始化为 NULL(所有字节的值都是 0),其他所有变量的初始值是未定义的。
3. 左值(Lvalues)和右值(Rvalues)
C++ 中有两种类型的表达式:
- 左值(lvalue):指向内存位置的表达式被称为左值(lvalue)表达式。左值可以出现在赋值号的左边或右边。
- 右值(rvalue):术语右值(rvalue)指的是存储在内存中某些地址的数值。右值是不能对其进行赋值的表达式,也就是说,右值可以出现在赋值号的右边,但不能出现在赋值号的左边。
变量是左值,因此可以出现在赋值号的左边。数值型的字面值是右值,因此不能被赋值,不能出现在赋值号的左边。下面是一个有效的语句:
int g = 20;
但是下面这个就不是一个有效的语句,会生成编译时错误:
10 = 20;
4. 代码示例
#include <iostream>
using namespace std;
// 变量声明
extern int a, b;
extern int c;
extern float f;
int main ()
{
// 变量定义
int a, b;
int c;
float f;
// 实际初始化
a = 10;
b = 20;
c = a + b;
cout << c << endl ;
f = 50.0/5.0;
cout << f << endl ;
return 0;
}
5. 变量作用域
一般来说有三个地方可以定义变量:
-
在函数或一个代码块内部声明的变量,称为局部变量。
-
在函数参数的定义中声明的变量,称为形式参数。
-
在所有函数外部声明的变量,称为全局变量。
作用域是程序的一个区域,变量的作用域可以分为以下几种:
-
局部作用域:在函数内部声明的变量具有局部作用域,它们只能在函数内部访问。局部变量在函数每次被调用时被创建,在函数执行完后被销毁。
-
全局作用域:在所有函数和代码块之外声明的变量具有全局作用域,它们可以被程序中的任何函数访问。全局变量在程序开始时被创建,在程序结束时被销毁。
-
块作用域:在代码块内部声明的变量具有块作用域,它们只能在代码块内部访问。块作用域变量在代码块每次被执行时被创建,在代码块执行完后被销毁。
-
类作用域:在类内部声明的变量具有类作用域,它们可以被类的所有成员函数访问。类作用域变量的生命周期与类的生命周期相同。
注意:如果在内部作用域中声明的变量与外部作用域中的变量同名,则内部作用域中的变量将覆盖外部作用域中的变量。
局部变量
在函数或一个代码块内部声明的变量,称为局部变量。它们只能被函数内部或者代码块内部的语句使用。下面的实例使用了局部变量:
#include <iostream>
using namespace std;
int main ()
{
// 局部变量声明
int a, b;
int c;
// 实际初始化
a = 10;
b = 20;
c = a + b;
cout << c;
return 0;
}
全局变量
在所有函数外部定义的变量(通常是在程序的头部),称为全局变量。全局变量的值在程序的整个生命周期内都是有效的。
全局变量可以被任何函数访问。也就是说,全局变量一旦声明,在整个程序中都是可用的。下面的实例使用了全局变量和局部变量:
#include <iostream>
using namespace std;
// 全局变量声明
int g;
int main ()
{
// 局部变量声明
int a, b;
// 实际初始化
a = 10;
b = 20;
g = a + b;
cout << g;
return 0;
}
在程序中,局部变量和全局变量的名称可以相同,但是在函数内,局部变量的值会覆盖全局变量的值。下面是一个示例:
#include <iostream>
using namespace std;
// 全局变量声明
int g = 20;
int main ()
{
// 局部变量声明
int g = 10;
cout << g;
return 0;
}
块作用域
块作用域指的是在代码块内部声明的变量:
#include <iostream>
int main() {
int a = 10;
{
int a = 20; // 块作用域变量
std::cout << "块变量: " << a << std::endl;
}
std::cout << "外部变量: " << a << std::endl;
return 0;
}
内部的代码块中声明了一个名为 a 的变量,它与外部作用域中的变量 a 同名。内部作用域中的变量 a 将覆盖外部作用域中的变量 a,在内部作用域中访问 a 时输出的是20,而在外部作用域中访问 a 时输出的是 10。
类作用域
类作用域指的是在类内部声明的变量:
#include <iostream>
class MyClass {
public:
static int class_var; // 类作用域变量
};
int MyClass::class_var = 30;
int main() {
std::cout << "类变量: " << MyClass::class_var << std::endl;
return 0;
}
MyClass 类中声明了一个名为 class_var 的类作用域变量。可以使用类名和作用域解析运算符 :: 来访问这个变量。在 main() 函数中访问 class_var 时输出的是 30。
6. 初始化局部变量和全局变量
当局部变量被定义时,系统不会对其初始化,您必须自行对其初始化。定义全局变量时,系统会自动初始化为下列值:
数据类型 | 初始化默认值 |
---|---|
int | 0 |
char | '\0' |
float | 0 |
double | 0 |
pointer | NULL |