??xml version="1.0" encoding="utf-8" standalone="yes"?> 一直都把堆栈放一P所以很多h会误以ؓ他们的组合是一个词语,像“衣服”一L单,其实不然Q今天在下就最q学习ȝ的一些与大家分n?/span> 一个由C/C++~译的程序占用的内存分ؓ以下几个部分Q?/span> 1、栈区(stackQ:又编译器自动分配释放Q存攑և数的参数|局部变量的值等Q其操作方式cM于数据结构的栈?/span> 2、堆区(heapQ:一般是q序员分配释放Q若E序员不释放的话Q程序结束时可能?/span>OS回收Q值得注意的是他与数据l构的堆是两回事Q分配方式倒是cM于数据结构的链表?/span> 3、全局区(staticQ:也叫静态数据内存空_存储全局变量和静态变量,全局变量和静态变量的存储是放一块的Q初始化的全局变量和静态变量放一块区域,没有初始化的在相ȝ另一块区域,E序l束后由pȝ释放?/span> 4、文字常量区Q常量字W串是攑֜q里Q程序结束后ql释放?/span> 5、程序代码区Q存攑ևC的二q制代码?/span> 堆和栈的区别Q?/span> 一、由以上lD可以得知,他们E序的内存分配方式不同?/span> 二、申请和响应不同Q?/span> 1、申h式:stackql自动分配,heap需要程序员自己甌Q?/span>C中用函数malloc分配I间Q用free释放Q?/span>C++?/span>new分配Q用delete释放?/span> 2、申请后pȝ的响应: 栈:只要栈的剩余I间大于所甌的空_体统ؓE序提供内存Q否则将报异常提C栈溢出?/span> 堆:首先应该知道操作pȝ有一个记录内存地址的链表,当系l收到程序的甌Ӟ会遍历该链表Q寻扄一个空间大于所甌的空间的堆结点,然后该l点从空闲结炚w表中删除Qƈ该l点的空间分配给E序。另外,对于大多数系l,会在q块内存I间中的首地址处记录本ơ分配的大小Q这样代码中?/span>delete?/span>free语句p够正的释放本内存空间。另外,׃扑ֈ的堆l点的大不一定正好等于申L大小Q系l会多余的那部分重新放入空闲链表中?/span> 三?/span> 甌的大限制不同: 栈:?/span>windows下,栈是向低地址扩展的数据结构,是一块连l的内存区域Q栈的地址和栈的最大容量是pȝ预先规定好的Q能从栈获得的空间较?/span> 堆:堆是向高地址扩展的数据结构,是不q箋的内存区域,q是׃pȝ是由链表在存储空闲内存地址Q自然堆是不连l的内存区域Q且链表的遍历也是从低地址向高地址遍历的,堆得大小受限于计机pȝ的有效虚拟内存空_由此I间Q堆获得的空间比较灵z,也比较大?/span> 四、申L效率不同Q?/span> 栈:栈由pȝ自动分配Q速度快,但是E序员无法控制?/span> 堆:堆是有程序员自己分配Q速度较慢Q容易生碎片,不过用v来方ѝ?/span> 五、堆和栈的存储内容不同: 栈:在函数调用时Q第一个进栈的是主函数中函数调用后的下一条指令的地址Q然后是函数的各个参敎ͼ在大多数?/span>C~译器中Q参数是从右往左入栈的Q当本次函数调用l束后,局部变量先出栈Q然后是参数Q最后栈指针指向最开始存的地址Q也是dC的下一条指令?/span> 堆:一般是在堆得头部用一个字节存攑֠得大,具体内容q序员安排?/span>
]]>#include <stdio.h>
int do_dup(int a[],int n);
void main()
{
int a[]={1,3,2,3};
do_dup(a,4);
}
int do_dup(int a[],int n)
{
int i;
int *b=new int[n];
for (i=0;i<n;i++)
b[i]=0;
for (i=0;i<n;i++)
{
if (b[a[i]]==0)
{
b[a[i]]=a[i];
}
else
printf("%d\n",b[a[i]]);
}
delete []b;
return 0;
}
]]>
double: 16位精?/p>
使用virtual的地方还?span style="color: red">虚拟l承和虚?span style="color: red">析构函数?br />
例子Q?br />
class SubClass : virtual public BaseClass 中以virtual声明的基c!Q由于C++支持多重l承Q所以对于一个派生类中有几个直接父类Q而几个直接父cM有几个可能分别承自某一个基c(是父类的父c)Q这样在构造最l派生类Ӟ会出现最l派生类中含有多个同一个基cȝ情况Q就会生二义性的问题Q不知道该调用哪个基cȝ成员变量和函敎ͼQؓ解决此问题,需要用虚基类Q即只对此基cȝ成一块内存区域,q样最l派生类中就只会含有一个基cM?br />
虚拟l承的作用:解决由多l承中,父类中可能有相同的父c而引发的二义性问题。虚拟承的虚拟和虚拟函数的虚拟没有M关系?/p>