Robotics StackExchange | Archived questions

rospy.get_param gives strings instead of negative values in a list

Hello,

I am trying to pass a matrix through a param.yaml file to be read by a python file. I am following the advice here with the exception that I am using rospy rather than roscpp. So I have formatted my .yaml file to include my 6x6 matrix as a flat list, however when I go to read it in and reshape it back into a matrix using rospy.get_param, I end up with a list full of floats for the positive values, and strings for the negative ones. I want to avoid having to use a for loop to go through each entry of the matrix and typecast these strings back into floats, but I'm at a loss for how else to get my matrix through the param server. How else can I get it to read my negative values as floats instead of strings? I've put a minimal example below.

the param.yaml file:

matrix: [1.0,0.0,0.0,0.0,0.0,0.0,  0.0,-1.9,0.0,0.0,0.0,0.0,  0.0,0.0,1.0,0.0,0.0,0.0,  0.0,0.0,1.0,0.0,0.0,0.0,  0.0,0.0,1.0,0.0,0.0,1.0,  0.0,0.0,1.0,0.0,1.0,1.0]

loaded through a launch file within the appropriate node:

<rosparam file='param.yaml' command='load'/>

called within the node as:

 if rospy.has_param('~matrix'):
    listmatrix=rospy.get_param('~matrix')
    toarray=np.array(listmatrix)
    self.matrix=toarray.reshape(6,6)
    rospy.loginfo(str(type(listmatrix[0])) + str(type(listmatrix[7])))
    rospy.loginfo(str(type(toarray[0])) + str(type(toarray[7])))
    rospy.loginfo(str(type(self.matrix[0,0])) + str(type(listmatrix[1,1])))

which returns

[INFO] [########.####, ########]: <class 'float'><class 'str'>
[INFO] [########.####, ########]: <class 'numpy.str_'><class 'numpy.str_'>
[INFO] [########.####, ########]: <class 'numpy.str_'><class 'numpy.str_'>

update: I've just checked in an attempt to debug, and it actually does this with any negative value I try to pass as a parameter, not just ones in lists.

second update: I checked on values I pass through either the launch file or the terminal, and they come back as floats, it is only ones loaded through .yaml files (and I fixed a typo, as per Mike's comment)

Asked by zippyzoo77 on 2022-09-01 15:46:28 UTC

Comments

Could the minus character in your yaml file be some other similar-looking character? Check the file using xxd -g 1 matrix.yaml utility and confirm the minus is a single byte hex 2d.

Asked by Mike Scheutzow on 2022-09-03 07:42:31 UTC

It is a 2d yes.

Asked by zippyzoo77 on 2022-09-06 11:20:16 UTC

Answers

You must pass a string argument to the methods. This returns a list of all floats for me:

a =  rospy.get_param('matrix')

Also, make sure you are not confusing 'matrix' and '~matrix'.

Asked by Mike Scheutzow on 2022-09-02 07:40:01 UTC

Comments

Oh, shoot yea, that was an error in my typing up of the example, the actual code I am running already had that in it. Also the ~ in the beginning the string indicates that it is a private parameter, in the case of the example it should work fine either way, but you use the private one when you want the parameter under the same namespace as what you are working on. In my code I am using the same piece of code under several namespaces, so using the ~ means I can use the same python file for all the namespaces, instead of having to customize each one that needs the matrix with 'robotx/matrix' as the string.

Asked by zippyzoo77 on 2022-09-02 12:51:43 UTC

Oh, shoot yea, that was an error in my typing up of the example, the actual code I am running already had that in it.

always copy actual code (snippets) when asking questions.

Paraphrasing / reformulating / reimplementing / etc has a high chance of wasting everybodies time.

Asked by gvdhoorn on 2022-09-06 03:21:58 UTC

Were that possible I would, unfortunately I do not have that luxury, and am forced to go about it this way instead. It would be so much easier and better, I agree, but alas. Please do not assume that everyone is working under situations that allow them to do that. I'm doing the best I can.

Asked by zippyzoo77 on 2022-09-06 11:15:53 UTC

In that case you'd create an MRE (Minimal Reproducible Example), verify the problem you've observed still is a problem in the MRE, then share the MRE.

Asked by gvdhoorn on 2022-09-06 11:59:30 UTC

As I have done above. But that still doesn't make it possible for me to copy and paste from one computer that cannot be connected to the internet and doesn't have the capability to write to disks to another computer that can only read data from an external source if it is on a read-only disk. (And no, this situation is not by choice, I hate the setup for so many reasons, of which not being able to transfer between my working machine and the internet is very near the top of the list). I still have to type it in manually, and I'm a human, I make the occasional typo. If I could do a copy and paste of the exact code (be it an MRE or the actual code) I would absolutely do so. I hate having to type the code manually (not only because I make human errors, but also because it is a huge duplication of my effort to write and test the code on one machine then type it into another), but I don't have the option to copy and paste.

Asked by zippyzoo77 on 2022-09-06 12:16:15 UTC