Regular nodes use TCP. This works fine for a lot of things. But if you have multiple processes that need to use messages that contain large amounts of data (like images or point clouds), packaging the message, sending it, then unpacking it can take a bit of time. If the two processes are on the same computer, it is quicker to just send a pointer to that data rather than sending the data itself over TCP.This only works for processes (aka nodelets) on the same computer though since a pointer for one computer doesn’t make sense for another computer. Nodes on the other hand can work over networked computers since you’re sending the actual data.So nodelets don’t make the processes quicker, but it is a quicker way to get information from one process to another. A good rule of thumb would be to always use nodes (because they are easier to use, and more flexible) unless you get in a situation where the message passing is too slow for your application and causing problems, then you would consider using nodelets.
那篇文章的核心内容基本都在这张图片上与上面这段话。下面进行简单的概括。
ROS::Node提供了类似于DNS的一个访问机制,常用的一个机制就是TCP/IP协议。也就是说,Node之间的通信必须经过握手等处理。这就意味着无意义的订阅最好取消掉,以节省内存。但Node的优势在于使用简单,极易扩展,并且可以作用在不同的终端上。比如某些进程在工控机运行,有些则在个人终端运行。
ROS::Nodelet是为了解决传递图片,点云这种大容量数据做的解决方案。其本质就是使用了C++的智能指针,用传递指向数据块的指针,来代替Node中对数据的传输。也就是说,其实是C++编程中传值与传址的差别。不过,这种方法显然只能用于一台机子的情况,因为指针只对其所在的机子内存有意义。
关于如何去选择,ROS给的建议是,经验告诉我们,通常使用node,除非你发现制约你应用的主要是在于传输数据上的耗时。
私货:
在任乾的开源算法中,使用了node,应该是出于简单考虑。为了解决大城市环境中点云需要占据大量的内存的问题,他在后端将关键帧点云(点云直接来自预处理阶段,即未下采样)存入到硬盘里,(闭环检测时的局部地图就是从硬盘里读取关键帧得来的,前端滑窗配准用的局部地图是用一个deque来存储的,即在内存中随着新关键帧的到来刷新)。不过加上了地板检测以后,相当于前端,后端,地板检测,闭环检测都订阅了预处理的点云,可能会对通信速度有影响吧。目前,还能忍受。
在koide的开源算法hdl中,使用了nodelet,因此肆无忌惮的设置订阅与发布,不过这也意味着只要还有一个订阅者存在,那么点云就必须存储在内存中供其使用。如果想要引入硬盘存储,则应该独立出一个管理点云信息的nodelet,由他去读取和存储。即便如此,显然依然得保证只有这个nodelet自己在引用点云数据。这说明得动态的去绑定和解绑,我觉得反而显得繁琐了。
因此,在自己的实现里依然应当选择node,直到实时性成为瓶颈,再考虑优化事宜。