菜鸟教程 -- 学的不仅是技术,更是梦想!

C++ 教程
C++ 教程 C++ 简介 C++ 环境设置 C++ 基本语法 C++ 注释 C++ 数据类型 C++ 变量类型 C++ 变量作用域 C++ 常量 C++ 修饰符类型 C++ 存储类 C++ 运算符 C++ 循环 C++ 判断 C++ 函数 C++ 数字 C++ 数组 C++ 字符串 C++ 指针 C++ 引用 C++ 日期 & 时间 C++ 基本的输入输出 C++ 结构体(struct) C++ vector 容器 C++ 数据结构

C++ 面向对象

C++ 类 & 对象 C++ 继承 C++ 重载运算符和重载函数 C++ 多态 C++ 数据抽象 C++ 数据封装 C++ 接口(抽象类)

C++ 高级教程

C++ 文件和流 C++ 异常处理 C++ 动态内存 C++ 命名空间 C++ 模板 C++ 预处理器 C++ 信号处理 C++ 多线程 C++ Web 编程

C++ 资源库

C++ STL 教程 C++ 导入标准库 C++ 标准库 C++ 有用的资源 C++ 实例 C++ 测验 C++ <iostream> C++ <fstream> C++ <sstream> C++ <iomanip> C++ <array> C++ <vector> C++ <list> C++ <forward_list> C++ <deque> C++ <stack> C++ <queue> C++ <priority_queue> C++ <set> C++ <unordered_set> C++ <map> C++ <unordered_map> C++ <bitset> C++ <algorithm> C++ <iterator> C++ <functional> C++ <numeric> C++ <complex> C++ <valarray> C++ <cmath> C++ <string> C++ <regex> C++ <ctime> C++ <chrono> C++ <thread> C++ <mutex> C++ <condition_variable> C++ <future> C++ <atomic> C++ <type_traits> C++ <typeinfo> C++ <exception> C++ <stdexcept> C++ <cstdio> C++ <cstdint> C++ <memory> C++ <new> C++ <utility> C++ <random> C++ <locale> C++ <codecvt> C++ <cassert> C++ <cwchar> C++ <climits> C++ <cfloat> C++ <cstdlib> C++ <numbers> C++ OpenCV
(追記) (追記ここまで)

C++ 修饰符类型

C++ 允许在 char、int 和 double 数据类型前放置修饰符。

修饰符是用于改变变量类型的行为的关键字,它更能满足各种情境的需求。

下面列出了数据类型修饰符:

  • signed:表示变量可以存储负数。对于整型变量来说,signed 可以省略,因为整型变量默认为有符号类型。

  • unsigned:表示变量不能存储负数。对于整型变量来说,unsigned 可以将变量范围扩大一倍。

  • short:表示变量的范围比 int 更小。short int 可以缩写为 short。

  • long:表示变量的范围比 int 更大。long int 可以缩写为 long。

  • long long:表示变量的范围比 long 更大。C++11 中新增的数据类型修饰符。

  • float:表示单精度浮点数。

  • double:表示双精度浮点数。

  • bool:表示布尔类型,只有 true 和 false 两个值。

  • char:表示字符类型。

  • wchar_t:表示宽字符类型,可以存储 Unicode 字符。

修饰符 signed、unsigned、long 和 short 可应用于整型,signedunsigned 可应用于字符型,long 可应用于双精度型。

这些修饰符也可以组合使用,修饰符 signedunsigned 也可以作为 longshort 修饰符的前缀。例如:unsigned long int

C++ 允许使用速记符号来声明无符号短整数无符号长整数。您可以不写 int,只写单词 unsigned、shortlong,int 是隐含的。例如,下面的两个语句都声明了无符号整型变量。

signed int num1 = -10; // 定义有符号整型变量 num1,初始值为 -10
unsigned int num2 = 20; // 定义无符号整型变量 num2,初始值为 20
short int num1 = 10; // 定义短整型变量 num1,初始值为 10
long int num2 = 100000; // 定义长整型变量 num2,初始值为 100000
long long int num1 = 10000000000; // 定义长长整型变量 num1,初始值为 10000000000
float num1 = 3.14f; // 定义单精度浮点数变量 num1,初始值为 3.14
double num2 = 2.71828; // 定义双精度浮点数变量 num2,初始值为 2.71828
bool flag = true; // 定义布尔类型变量 flag,初始值为 true
char ch1 = 'a'; // 定义字符类型变量 ch1,初始值为 'a'
wchar_t ch2 = L'你'; // 定义宽字符类型变量 ch2,初始值为 '你'

为了理解 C++ 解释有符号整数和无符号整数修饰符之间的差别,我们来运行一下下面这个短程序:

实例

#include<iostream>usingnamespacestd; /* * 这个程序演示了有符号整数和无符号整数之间的差别 */intmain(){shortinti; // 有符号短整数shortunsignedintj; // 无符号短整数j = 50000; i = j; cout << i << "" << j; return0; }

当上面的程序运行时,会输出下列结果:

-15536 50000

上述结果中,无符号短整数 50,000 的位模式被解释为有符号短整数 -15,536。

C++ 中的类型限定符

类型限定符提供了变量的额外信息,用于在定义变量或函数时改变它们的默认行为的关键字。

限定符含义
constconst 定义常量,表示该变量的值不能被修改。
volatile修饰符 volatile 告诉该变量的值可能会被程序以外的因素改变,如硬件或其他线程。。
restrictrestrict 修饰的指针是唯一一种访问它所指向的对象的方式。只有 C99 增加了新的类型限定符 restrict。
mutable mutable 用于修饰类的成员变量。被 mutable 修饰的成员变量可以被修改,即使它们所在的对象是 const 的。
static 用于定义静态变量,表示该变量的作用域仅限于当前文件或当前函数内,不会被其他文件或函数访问。
register 用于定义寄存器变量,表示该变量被频繁使用,可以存储在CPU的寄存器中,以提高程序的运行效率。

在 C++11 中被标记为弃用(deprecated) 在 C++17 中被正式移除。

const 实例

const int NUM = 10; // 定义常量 NUM,其值不可修改
const int* ptr = &NUM; // 定义指向常量的指针,指针所指的值不可修改
int const* ptr2 = &NUM; // 和上面一行等价

volatile 实例

volatile int num = 20; // 定义变量 num,其值可能会在未知的时间被改变

mutable 实例

class Example {
public:
 int get_value() const {
 return value_; // const 关键字表示该成员函数不会修改对象中的数据成员
 }
 void set_value(int value) const {
 value_ = value; // mutable 关键字允许在 const 成员函数中修改成员变量
 }
private:
 mutable int value_;
};

static 实例

void example_function() {
 static int count = 0; // static 关键字使变量 count 存储在程序生命周期内都存在
 count++;
}

register 实例

void example_function(register int num) {
 // register 关键字建议编译器将变量 num 存储在寄存器中
 // 以提高程序执行速度
 // 但是实际上是否会存储在寄存器中由编译器决定
}

C++11 后 register 的变化:

  • 在 C++11 中被标记为弃用(deprecated)
  • 在 C++17 中被正式移除
  • 保留为关键字(可能用于兼容或未来用途)
AI 思考中...

5 篇笔记 写笔记

  1. #0

    g_t

    gt@***ms.org

    参考地址

    214

    C++提供了关键字explicit,可以阻止不应该允许的经过转换构造函数进行的隐式转换的发生。声明为explicit的构造函数不能在隐式转换中使用。

    C++中, 一个参数的构造函数(或者除了第一个参数外其余参数都有默认值的多参构造函数), 承担了两个角色。 1 是个构造器 ,2 是个默认且隐含的类型转换操作符。

    所以, 有时候在我们写下如 AAA = XXX, 这样的代码, 且恰好XXX的类型正好是AAA单参数构造器的参数类型, 这时候编译器就自动调用这个构造器, 创建一个AAA的对象。

    这样看起来好象很酷, 很方便。 但在某些情况下(见下面权威的例子), 却违背了我们(程序员)的本意。 这时候就要在这个构造器前面加上explicit修饰, 指定这个构造器只能被明确的调用/使用, 不能作为类型转换操作符被隐含的使用。

    explicit构造函数的作用

    解析:

    explicit构造函数是用来防止隐式转换的。请看下面的代码:

    class Test1
    {
    public:
     Test1(int n)
     {
     num=n;
     }//普通构造函数
    private:
     int num;
    };
    class Test2
    {
    public:
     explicit Test2(int n)
     {
     num=n;
     }//explicit(显式)构造函数
    private:
     int num;
    };
    int main()
    {
     Test1 t1=12;//隐式调用其构造函数,成功
     Test2 t2=12;//编译错误,不能隐式调用其构造函数
     Test2 t2(12);//显式调用成功
     return 0;
    }

    Test1的构造函数带一个int型的参数,代码23行会隐式转换成调用Test1的这个构造函数。而Test2的构造函数被声明为explicit(显式),这表示不能通过隐式转换来调用这个构造函数,因此代码24行会出现编译错误。

    普通构造函数能够被隐式调用。而explicit构造函数只能被显式调用。

    g_t

    gt@***ms.org

    参考地址

    9年前 (2017年06月09日)
  2. #0

    菠萝1988

    pxf***[email protected]

    55

    volatile 往往会用于多线程的修饰,比如:

    volatile boolean isNext = false;
    Thread A() {
     // 第一个工作
     // isNext = true;
    }
    Thread B (){
     if (isNext) {
     // 第二个工作
     }
    }

    这里volatile 就是从来标记isNext, 以确保线程B每次都重新从内存中读取isNext的值,第二个工作一定在第一个工作之后进行。

    但是要注意,这里无法保证顺序性,应该编译器编译的时候会重新打乱两个语句的先后顺序,因此做第一个工作和赋值给isNext不一定会按照你代码顺序正常执行。

    更多内容可参考:C/C++ 中 volatile 关键字详解

    菠萝1988

    pxf***[email protected]

    9年前 (2017年09月21日)
  3. #0

    arzel

    123***[email protected]

    202

    对于无符号化为有符号的位数运算,采取 N-2^n 的计算方法,n 取决于定义的数据类型 int、short、char、long int 等等,N 为无符号数的数值,例如文中的 N=50000,short 为 16 位,计算方法为 50000-2^16 得到 -15536。

    arzel

    123***[email protected]

    8年前 (2018年06月12日)
  4. #0

    小阔爱

    294***[email protected]

    102

    16 位整数(短整数)的情况下,十进制 50000 就是二进制 11000011 01010000 但在有符号的情况下,二进制最左边的 1,代表这整个数字是负数但是电脑是以补码形式来表示数字的,要获得原本的数字,首先要把整个二进制数 - 11100001101010000 - 1 = ‭1100001101001111‬ 然后,在把答案取反码 not ‭1100001101001111‬ = ‭0011110010110000‬ 把最终答案变成十进制,就是 15536 所以,一开始的二进制数 11000011 01010000,在有符号的情况下代表的就是 -15536

    来自网友牢记圣光的笔记:

    //上边的例子的二进制数为下边的运行结果,看到二进制就很好理解了!
    #include <iostream>
    #include <cstdlib>
    using namespace std;
    int main()
    {
     short int i; // 有符号短整数
     short unsigned int j; // 无符号短整数
     j = 50000;
     i = j;
     cout <<"i:" <<i<<'\n'<< "j:" << j<<endl;
     char s[40];
     _itoa_s(i, s, 2);
     printf("变量i的二进制数为:%s\n", s);
     _itoa_s(j, s, 2);
     printf("变量j的二进制数为:%s\n", s);
     return 0;
    }

    结果为:

    i:-15536
    j:50000
    变量i的二进制数为:11111111111111111100001101010000
    变量j的二进制数为:1100001101010000

    小阔爱

    294***[email protected]

    8年前 (2018年07月23日)
  5. #0

    adults

    223***[email protected]

    24

    验证 const

    #include<iostream> 
    using namespace std;
    int main()
    {
     const float PI = 3.14;
     PI = 3; //尝试修改 PI 的值,将会出现错误提示。
     float radius = 10.0;
     float area = PI * radius * radius;
     float circumference = 2 * PI * radius;
     cout << "area is "<<area <<", circumference is "<< circumference<<endl;
     return 0;
    }

    更多 C++ const 关键字参考:C++ const 关键字小结

    adults

    223***[email protected]

    8年前 (2018年11月01日)

点我分享笔记

  • 昵称 (必填)
  • 邮箱 (必填)
  • 引用地址

AltStyle によって変換されたページ (->オリジナル) /