Ask Your Question
0

ROS with multiple classes

asked 2020-03-21 10:26:44 -0500

Hyperion gravatar image

updated 2020-03-21 10:35:04 -0500

Hi people!

I built a system integrating ROS with EtherLAB to communicate with a machine. To perform the control, I also built a HMI using PyQt5. So I have a piece of code written in C ++ (EtherLAB) and a portion made in Python. Both programs has publishers and subscribers and I use ROS to interconnect them.

The process works normally, but when I add several classes, the system loses a lot of performance. In this case I have several classes (in Python):

class db_connect(object):
    # Some stuff to connect with DB

class ROSController(db_connect):
    # Some code to create the node, publishers and subscribers and also the logic behind the system
    # Has an __init__ method that allows the beginning that creates the publishers and subscribers

class MainController(ROSController):
    # Class that creates the interconnection between graphical intreface and logic. In addition to integrating the functionallity between all windows.
    # this is the CLASS that is instantiated by the function def main() of python in order to execute the program.
    # this class have methods to call another windows, such as Window_1, Window_2, Window_3 and so on.

class Window_1(ROSController):
    # Main window containing buttons and other things.
    # ALL WINDOWS ARE MADE USING QTDESIGNER and exported using pyuic command.

class Window_2(ROSController):
    # Another window, this responsible for checking the read data of sensors.

class Window_3(ROSController):
    # Another window, this responsible to trigger some actuators.

And so on...

The problem is that every time a class that inherits from ROSController seems to restart all nodes, publishers and subscribers. Creating new instances that should not exist and thus generating threads that apparently slow the program. The curious thing is that the activation of the actuators occur in near real time (about 10 ms). But reading a sensor, for example, takes 4 to 5 seconds to be recognized.

Over time, the system memory consumption increases and freezing the server. I have seen that is not the EtherLAB or the PyQt5, but can be the ROS itself. But I do not know how to fix.

This machine needs to work 24/7 without interruption of anykind.

In short (TL: DR): What is the best way to call a class that contains the methods of publish and subscribe in order to be used for several other classes without losing or reset the previous values ​​(keep the consistency of information) and so that it is thread safe?

Thank you and excuse me for my English.

edit retag flag offensive close merge delete

1 Answer

Sort by » oldest newest most voted
0

answered 2020-04-24 07:05:16 -0500

Hyperion gravatar image

I solved this problem thanks for a tip of Edouard Renard (Udemy: ROS for Beginners Course). I implemented a singleton in each class and I did not use inheritance, but composition. This helped me to solve the problem. The code was something like this:

class db_connect(object):
     # Some stuff to connect with DB

class ROSController(objetc):
       # singleton flag
    _instance = None

    @classmethod
    def instance(cls):
        if cls._instance is None:
            cls._instance = cls()
        return cls._instance

    def __init__(self, parent=None):
        super(ROSController, self).__init__(parent)
        ...

class MainController(db_connect):
    def __init__(self):
        super(MainController, self).__init__()
        self.ros_node = RosController.instance()

class Window_1(object):
    # Main window containing buttons and other things.
    def __init__(self):
        super(Window_1, self).__init__()
        self.setupUi(self)
        self.ros_node = RosController.instance()
edit flag offensive delete link more

Your Answer

Please start posting anonymously - your entry will be published after you log in or create a new account.

Add Answer

Question Tools

1 follower

Stats

Asked: 2020-03-21 10:26:44 -0500

Seen: 210 times

Last updated: Apr 24 '20