c++应用程序优化之一变量内存的优化

224 篇文章 92 订阅

c++应用程序优化之一变量内存的优化

c++可优化的细节非常多,从这次起开始一个个的说明一下,有些是来自书本,有些来自经验 ,有些来自网上的其它的一些资料,优化的方法是相同的,所以只介绍原理和方法。针对c++11及后续的c++新的版本库的一些特点,会对一些优化的细节进行综合说明。

一、字符串

字符串变量的优化是最常见的,也是最容易被忽略的。这里举一个简单的例子:

void Test(const std::string &s)
{

  std::string str;

  for (int num =0;num < s.length();num++)
  {
    str =str + s[i];//第一种
    //改写成:
    str += s[i];//第二种
  }  
}

如果用第一种的话,会产生临时字符串变量,也就是说分配内存N次,导致开销增加,在数据量巨大时,不可小觑。此外,这种连接表达式也会产生不必要的临时变量的产生,导致内存分配的增加。但是,在c++11的环境下,优秀的编译器会对此进行优化,利用移动构造函数来实现高效的指针复制。
如果涉及到大量的字符的处理,建议采用c的形式来处理而不是采用c++的字符串处理,这样虽然有点小麻烦,但是效率是最高的。

二、线性类容器的优化

其实其它的相关的线性容器都有类似的问题(比如上面的std::string也可以这样指定长度),看下面的代码:

std::vector<int> vec;
//vec.reserve(10000);//提前处理一下内存
for (int num =0;num < 10000;num++)
{
  vec.push_back(num);
}

在循环比较小的情况下,vector的内存再次分配造成的开销是可以容忍的,如果大到一定程序,连续的内存分配和数据拷贝会极大的降低性能。可以用reserve来提前处理一下内存长度(注释部分),让其和相关的实际数据匹配。

三、大内存对象的指针或者引用传递

这个非常容易理解,如果向一个函数传递一个拥有较大的内存变量时,或者需要返回一个此类的对象时,临时对象的复制开销也是相当巨大的。因此,可以考虑使用引用或者指针来搞定,看下面的例子:

typedef struct __List__
{
  int d;
  char buf[100];
}MyList,*PMyList;

MyList GetValue(MyList oldlist)
{
  MyList list;
  ......
  return list;
}

int GetValue(MyList &old,Mylist &new)
{
  new.d = old.d + 1;
  ....

  return 0;
}

这样会大幅的减少临时变量的开销,提高效率。

四、移动语义

在c++11实现了移动语义后,拷贝构造函数的引用可以不再使用了,类似如下:

class String
{
public:
  ...
  //C++98:
  //String(const String& s);
  //String& operator=(const String& s);
  //C++11:
  String(String s);
  String& operator=(String s);
  ...
};

这个陈硕在网上有相关的评论,主要主是移动语义起得作用。这个目前还有一些争论,这里提出这个的目的是,一定要利用好c++11的移动语义来减少开销。
另外,在创建智能指针时尽量使用std::make_shared, 同样也是基于这个道理。

五、总结

这里总结得很唐突,只是想把这个开一个头,好不断的向前推进整个优化的总结。一点点先记下来,回头再整体统一进行整理。

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值