C++内存模型
1.存储持续性描述数据在内存中的保留时间。自动存储持续性静态存储持续性动态存储持续性2.作用域描述名称在翻译单元文件的可见范围。声明区域 declaration region可以在其中进行声明的区域。潜在作用域 potential scope从声明点开始到其声明区域的结尾。变量对程序而言可见的范围被称为作用域scope。3.链接性描述名称如何在不同翻译单元文件间共享。有3种值文件外部文件内部无。4..自动存储持续性变量在函数中声明的函数参数和变量的存储持续性为自动作用域为局部没有链接性。可以使用关键字auto来显示指出存储类别它极少被使用比如它可以表明程序中特意创建了一个自动变量它将暂时覆盖全局定义。寄存器变量是另一种形式的自动变量。使用关键字register提醒编译器用户希望它通过cpu寄存器而不是堆栈来处理特定的变量从而提供对变量的快速访问。如果变量被存储中寄存器中则没有内存地址不能将地址操作符用于寄存器变量。在编写for循环时编译器可能自动使用寄存器来存储循环计数。5.静态存储持续性变量由于静态变量的数目在运行期间是不变的程序不需要使用特殊装置如堆栈来管理它们将分配固定的内存块来所有静态变量。默认情况下静态数组和结构每个元素或成员的所有位都设置为0。只能使用常量表达式来初始化静态变量常量表达式包括字面值常量const常量enum常量sizeof操作符。传统的KR C不允许初始化自动数组和结构但允许初始化静态数组和结构。在代码块外声明的变量链接性为外部在代码块外声明的static变量链接性为内部在代码块内声明的static变量没有链接性5.1.外部链接性变量在函数外部定义也称为全局变量链接性为外部持续性为静态作用域为其所属的文件内外。自动变量将隐藏同名的外部变量。只能有一个文件中定义声明某个外部变量其它文件中可以使用extern来引用声明其它文件中定义声明过的外部变量在同一个文件中extern是可选的不能在引用声明中初始化变量初始化指的是在分配内存单元时给它赋值。例如extern double warming;在c中使用作用域操作解析符(::)来显示指出操作的是全局变量。5.2.内部链接性变量若要常规外部变量前加了static限定符则其变成内部变量链接性为内部持续性为静态作用域为文件内。内部变量将隐藏同名的外部变量。c标准指出使用static来创建内部链接性的方法将逐步被淘汰提供了另一种由名称空间来使用共享数据的方法。const全局变量链接性为内部的内部链接性还意味着每个文件都有自己的一组常量这就是能够将常量定义放在头文件中的原因。如果希望const全局变量链接性为外部可以再加上extern关键字。如extern const int state1;这与常规的定义声明不同多加了使用了extern其它引用声明形式不变。5.3.无链接性静态变量作用域在代码块中的静态持续性变量使用static限定符。6.cv-限定符cv-qualifiercv表示const和volatile不稳定的volatile表明即使程序没有对内存单元修改其值 也可能发生变化。mutable表明即使变量声明为const其值也可以被修改。较少使用。7.函数的存储持续性都是静态的链接性为外部即可以在文件间共享。可以在函数原型中用extern指出函数是在另一个文件中定义的这是可选的。可以使用static将函数的链接性设置为内部的要同时在函数原型和定义前使用static。单定义规则对于非内联函数程序中只能包含一个定义。同一个内联函数名的内联定义必须相同。8.语言链接性language linking。在c语言中一个名称只对应一个函数这是c语言链接性。在c中有同名函数的不同重载版本c编译器执行名称修饰将这些重载函数翻译成不同的符号名称这是c语言链接性。链接程序寻找函数时c函数和c函数有不同的方式。可能c仅根据函数名而c要根据函数名和参数名。为解决这个问题在函数原型前加上extern “C”或extern “C”来指出要使用的约定。例如 extern void spoff(int); 这样默认使用的是c语言链接约定。9.动态内存由操作符new和delete控制不是由作用域和链接性控件。虽然存储方案并不适用于动态内存但适用于用来跟踪动态内存的自动静态指针变量。使用new语句设置静态存储变量的代码必须在函数中因为只能使用常量表达式来初始化静态存储变量。在程序结束时由new分配的内存通常都将被释放但在不很健壮的操作系统中请求的大型内存块时可能不会被自动释放最佳的做法时使用delete释放。10.布局new操作符11.名称空间 namespace名称空间可以嵌套但不能位于代码块中默认情况下名称空间中声明的变量是外部链接性的除非它引用了常量。全局名称空间它对应于文件级声明区域。通过作用域 解析操作符::使用名称空间限定名称。名称空间结尾的大括号后面无分号。内存的分配方式:一、从静态存储区域分配。内存在程序编译的时候就已经分配好这块内存在程序的整个运行期间都存在。例如全局变量。二、在栈上创建。在执行函数时函数内局部变量的存储单元都可以在栈上创建函数执行结束时这些存储单元自动被释放。栈内存分配运算内置于处理器的指令集中效率很高但是分配的内存容量有限。三、从堆上分配亦称动态内存分配。程序在运行的时候用malloc或new申请任意多少的内存程序员自己负责在何时用free或delete释放内存。动态内存的生存期由我们决定使用非常灵活但问题也最多。