delphi中字符串于内存的问题

最近写了一个程序,发现运行时页面错误增量不停以2000/s的速度增加。通过不断注释,调试,最终定位问题出在在拼接sql语句中。

由于程序需要更新数据库,为了提高执行sql的效率,将多条sql拼在一起,一次刷新数据库。使用了sql=sql+str1的模式进行拼接。

实验一:

var
  str1, str2, str3: string;
begin
  str1 := 'delphi ';
  str2 := 'oracle';
  ShowMessage('str3='+IntToStr(Integer(str3)));
  str3 := str2+str1
  ShowMessage('str3='+IntToStr(Integer(str3)));
  str3 := str3+str1;
  ShowMessage('str3='+IntToStr(Integer(str3)));
end;

通过比较str3赋值前后指向堆的地址,发现str3前后的地址不一样,可以知道delphi中的string间加号操作符会内部申请一片空间,然后将右边的字符串拷贝过去。 而如果 只是str3:=str1;我们会发现str3指向的地址通str1指向的地址一样,其实只是增加了str1指向字符串的引用,当str1[1]:=#65;这时,str1指向的地址将会发生改变,str3指向的地址改变,这就是的delphi的 copy-on-write机制。 下面我们再来看第二个实验。

实验二:

var
  str4:string;
begin
 while True do
 begin
   GetMem(str4, 1024*1024 );
   FreeMem(str4)
 end;
end;

这时我们去观察windows任务管理其中的页面错误那一选项,我们会发现,页面的错误量会剧增。

把1024*1024换成小一点,1024*10,这是我们会发现页面错误数增长的慢一些。继续减小,当减小为1024*4时,我们发现,页面错误没有增长了。

我们可以得出结论,当申请大于页面的内存时(猜测),会产生页面错误。

所以程序中出现大量页面错误,是因为拼接的sql语句过长,超过十几K,而且有大量拼接,导致程序不断的申请内存进行字符串拷贝,最终导致页面错误暴涨。

对于分配大内存会产生页面错误的原因还未弄清楚,先附上一图:

 

 

转载于:https://www.cnblogs.com/wust0801/archive/2013/01/31/2888214.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值