编程踩坑记录

1, stl中的一些库, 比如map, unordered_map, 不要在遍历循环中做删除erase操作,该操作是一个undefined operation:

unordered_map<int, int> object.
for(auto item:object){
if(item->shoule_be_erazed )
object.erase(item->first)
}

但可以用迭代器来处理
for(auto iter=object.begin(); iter!= object.end()😉
if(item->shoule_be_erazed )
iter = object.erase(iter)
else
iter++;

也可以先统计好需要被erase掉的关键字, 然后再统一进行erase操作。
2, 函数返回值是Eigen对象时, 即使函数里没有return 函数, 也不会报错, 所以这个地方一定要注意。

3, 函数和变量的命名要让别人看见函数名就能知道该函数的大概功能。函数前最好写上功能说明。

4, new出来的对象, 最好在一个线程里管理。尽量用智能指针代替普通指针。

5, 传参stl变量传入的实际是指针(类似数组)还是值?

6, ubuntu电脑自带内存够的话, 关闭swap空间

7, 当通过key value来访问std::map, std::unordered_map时, 存在对其进行修改的可能, 所以当该容器定义为const时, 不能如此访问,而宜用.at来访问。

8, rosnode kill -a有时不会起到预期的效果, 此时可以用top查看进程, 然后用kill -9或者pkill -9 强制杀死相关ros进程

9, 多线程传参,不能引用传入一个临时变量, 因为退出函数后,开辟的线程单独运行,传入的引用参数已经被销毁了。
10, 在多线程的某个线程里运行过程中临时开辟的多线程a,在这个a线程里用opencv显示图片会有问题,这时只能把需要现实的图片取回到该线程里,才能正常显示。
11, include 文件顺序重新排列,会带来意想不到的错误,所以在.clang-format文件里要加上:SortIncludes: ‘false’
12, 函数里new 出来 一个g2o vertex 变量, 使用结束后delete, 退出函数的时候会出现double free的错误,这是g2o自备释放内存的功能吗?
原因 : 这些vertex指针加入到optimizer中之后, 最后会由optimizer来进行释放。
13,virtual 作用: 对于父类函数(virtual、非virtual),如果有同型函数:
----非virtual函数由指针类型决定调用哪个
----virtual函数由指针指向的对象决定调用哪个(运行时决定)
14, 函数使用Eigen对象作为返回值的时候,即使没有返回, 编译程序也不会报错,此处应该引起注意。

15, 使用auto注意, 有时需要进行值传递, 但结果可能是引用传递,造成对原值预料之外的修改。 特别是用auto定义一个Eigen对象的时候!

16, 使用指针没有初始化的指针将发生无法预料的结果,通常,一个没有赋值的指针可能指向任意地址,如果此时对指针执行了解除引用(即*pointer)操作,则可能改写内存中的信息,这可能导致正在引用该内存区的程序崩溃,严重时,程序将退出,但不会破坏程序本身,没有初始化的指针,判断该指针是否有效的时候,将得到指针有效的结果,例如

data* d1;
if(d1){ //True
}

data* d2 = nullptr;
if(d2){ //False
}

17,assert在debug模式下不起作用!!!
18, ros::NodeHandle nh 与 ros::NodeHandle nh("~")的区别:后者代表私有命名空间,其差异可体现在订阅话题和获取param参数上。具体见ros::NodeHandle
19, Image2 = Image1 与 Image2 = Image1.clone()的区别:

20, std::unordered_map 可以用 tuple做键值,但需要自定义hashkey。

#include "boost/functional/hash.hpp"
#include <string>
#include <unordered_map>
#include <cstring>
#include <iostream>
#include <tuple>


using Key = std::tuple<int, char, char>;

struct KeyHash {
    std::size_t operator()(const Key & key) const
    {
        return boost::hash_value(key);
    }
};

using Map = std::unordered_map<Key, int, KeyHash>;

int main()
{
    Map map;
    map[1,"c","b"] = 23;
    return 0;
}

21, ofstream 执行文件写操作,最后不关闭,可能导致写入内容不全。
22,boost_thread在栈上新建线程的问题。
23,记住:子类的初始化列表不能初始化父类或者祖先类的成员。
24, “pure virtual method called”:
25, “an inaccessible base”:
26, ros中的use_sim_time问题
在这里插入图片描述
27, CMakeLists.txt中解决本地库(如g2o)与ros库版本冲突问题: 如果要连接本地库,需要先include本地库对应的头文件所在目录,否则编译可能会通不过。编译通过后ldd可看到依然链接了ros的库,此时需要在运行窗口中将本地库所在路径加入到运行时库的搜索路径中(export LD_LIBRARY_PATH=YOUR_LIBRARY_PATH:$LD_LIBRARY_PATH);

28, 返回const &引用的问题

class Test{
int data;
const int &getData() {
return data;
}
};

int main(){
Test t;
auto d = t.getData();
d = 1;
return 0;
}

上述代码中,主函数可以对返回的data引用进行赋值,但并不会影响t对象中的data。

29: c++中std::sort底层方法可简称为快速排序分段递归,当数据量小的时候是插入排序,当数据量大的时候,是堆排序;堆排序能改善递归层数过深的问题。结果不稳定;
std::stable_sort则是稳定的排序。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值