https://oj.leetcode.com/problems/longest-palindromic-substring/
这个leetcode得出的,可能是这个原因,后面慢慢找出结果
const_reference operator[](size_type _Pos) const
{ // subscript nonmutable sequence
return (*(begin() + _Pos));
}
reference operator[](size_type _Pos)
{ // subscript mutable sequence
return (*(begin() + _Pos));
}
这个是stl里面的vector的[]操作,看上去是没差别啊,直接得到位移,不过我也觉得可能是因为vector需要预分配控件,而这个leetcode这个控件确实也是预分配的啊,搞不懂,后面有时间看看源码,有人测在debug下和release下结果不一样,debug下比release下多出10倍时间。
后面继续找一下这个原因。
————————————————————————————————————
接着,vector里面大量的虚构和构造够电脑受的了,如果需要高性能,还是自己new delete快一些,vector主要面向方便。而且,leetcode的代码应该是debug模式运行的?vs编译器本来就会对最后的代码调优,debug还原了很多调试信息,所以慢很多
而且最重要的原因是,我vector是循环嵌套的 like this vector<vector<int>>
这样会慢很多,多用数组吧。
————————————————————————————————————————————
接着,最新看到的
慢的原因是数据存储的局部性问题(data locality):
1) 使用二位数组Depart[500][21]的时候,所有数据在内存中是连续存放的。访问内存时,内存访问的局部性较强,Cache命中的概率较大。L1 Cache访问延迟只有几个指令周期,而内存访问延迟则达到几百个指令周期。
2)Vector中的数据是连续存放的,但是Vector本身只保存指向数据块的指针。Vector建立在栈上,保存数据的数据块在堆上。因此二位动态数组Vector <Vector<int>>中,指向行的所有指针是连续存放的。每个行的数据是连续存放的,但是行与行之间是不连续存放的。因此跨行访问时局部性降低,Cache命中率下降。所以用时间更多。
改进方案。提升数据局部性:
typedef int line[21];
Vector<line> Depart;