分类: C/C++

C/C++语言

11 篇文章

嵌入式C/C++技巧——嵌入式厂商对 C/C++ 的支持
C/C++有若干个版本,每个版本通常会引入或删除一些特性,嵌入式常用编译器通常至少支持C99/C++11,因此本教程低于或等于此版本的特性将不再标注版本,并且通常支持C11和C++17,因此本教程涉及的内容均以该标准为准。通常编译器不会实现标准的所有功能,因此是否实现了特定功能需要以手册为准。 编译器编译器版本支持的C版本支持的C++版本参考Arm Compiler for Embedded 66.22ISO C89, C99, C11(实际也支持GUN C90, C99, C11)ISO C+…
嵌入式C/C++技巧——目录
前言 第一章 C与C++ 从C到C++ 嵌入式厂商对C/C++的支持 C/C++不完全兼容 C++简单入门 变量与字面量 枚举 结构体、位域与联合体 初始化 预处理器 替换文本宏与有条件编译 包含其他文件 其他(错误或警告、由实现定义的行为) 弱函数 内联函数 变参数函数 类型转换 强制类型转换 隐式类型转换 C++标准库 array——数组的替代品 C/C++混合编译
嵌入式C/C++技巧——预处理器(包含其他文件)
包含其他文件(#include) #include用于将其他文件包含到当前这一行,即将此行替换为这个文件的全部内容,文件名使用尖括号<>或双引号""包裹,使用尖括号<>只会在标准库中查找,使用双引号""会优先查找源文件同级目录中的文件,若找不到则会按顺序查找包含路径中的文件,若依旧找不到文件时会回退到标准库中查找,一旦找到对应文件则停止查找。 例如在bsp.c中使用#include "bsp.h",则会首先在bsp.c所在的文件夹中进行查找,若没有找到则在包含路径中进行查…
嵌入式C/C++技巧——预处理器(替换文本宏、有条件编译)
预处理器用于编译前的源代码处理,替换文本宏与有条件编译经常搭配使用。 替换文本宏(#define、#undef、#、##)与有条件编译( #if、#ifdef、#ifndef、#else、#elif) 使用方法 替换文本宏系列 #define指令 替换文本宏用于定义一个标识符并通常与有条件编译搭配使用,或将标识符替换为指定替换列表,标识符通常被称为宏。替换文本宏有多种使用形式: #define 标识符 替换列表 (可选)(1)#define 标识符 (形参 )&nb…
使用VS Code浏览MDK工程
引子 众所周知,MDK的定义跳转和自动补全真的是一言难尽,没有编译的内容直接罢工跳转不了,自动补全也常年跳不出来,总想着要是能用VS Code看代码就好了。 如果直接用VS Code打开工程的话,又会报错满天飞,这个找不到路径,那个没有定义,为了解决这个问题,需要手动配置一下VS Code。 配置VS Code VS Code打开文件夹后,会读取.vscode/c_cpp_properties.json的C/C++配置文件,在这个文件里可以指定包含路径、定义等,c_cpp_properties.…
美国信息交换标准代码(ASCII)与转义序列(C/C++)表
美国信息交换标准代码(ASCII) 美国信息交换标准代码(American Standard Code for Information Interchange,ASCII)等同于国际标准ISO/IEC 646。 转义序列 (C/C++)转义序列是用来在字符串字面值中定义某些特殊字符。 转义序列描述表示简单转义序列(见ASCII表)数值转义序列\nnn任意八进制值代码单元 nnn(1~3 位八进制数位)\o{n...} (C++23 起)代码单元 n...(任意位数的…
算法工具——并查集
引子 并查集(disjoint-set data structure/union–find data structure)以不相交的子集的形式储存集合,它有以下功能: (并)合并两个子集 (查)查找元素所属子集(衍生:判断两个元素是否属于同一个子集) 实现(C++) 通常,并查集由树形结构实现。树储存在数组中,数组中的值代表父节点,若父节点为自己则代表为根节点。初始状态下,每个元素都属于独立的子集,即每个元素都是根节点。根据不同的策略(快查/快并)并查集的实现也不完全相同。 快查 在快查策略下,…
枚举在C、C++下兼容的问题
引子 在C++下,枚举的底层类型可以通过枚举基确定,但C下并不支持这种用法,因此在做两者兼容时可能会出现一些潜在的问题,例如: #ifdef __cplusplus namespace test { namespace impl { #endif enum test_enum { TEST_ENUM_1, TEST_ENUM_2, }; #ifdef __cplusplus } // namespace impl } // namespace utils namespace test { enu…
在调试器中查看指针指向的数组
引子 通常,指针在变量监视器中一般只会显示指针的地址和指向的内容,无法直观查看数组内容。 解决办法 在变量监视器中强制转换为数组类型,例如,添加一个长度为8的int类型数组(var为int *): (int [8])*var 即可在变量监视器中查看对应的数组。
重复包含、未包含头文件内容的问题
避免重复包含头文件的做法 众所周知,为了避免重复包含头文集,会使用这样的用定义来避免重复包含头文件。 #ifndef xxx_H #define xxx_H //头文件内容 #endif 在第一次#include这个头文件时,会#define xxx_H,在之后的重复包含的头文件时会由于#ifndef xxx_H不再包含头文件的内容,从而避免头文件重复包含。需要注意的是不同头文件#define xxx_H的内容需要不同,不然只能包含第一个头文件。 嵌套包含导致缺少定义 例如这三个文件有这样的包含…