ROS使用总结1-传参

ROS使用总结1-传参

[TOC]

背景

ROS 节点需要加载 csv 文件读取数据, 文件路径名需要通过参数传到程序里面, 考虑到代码共享, 每个人的 workspace 路径可能都不一样, 传进去的参数要是 Package/Node 的相对路径, 最好是通过 launch file 传入, 省得输入.
默认的加载路径是 workspace 的路径. 最初的想法是找到 Node 的 execuaable 的路径, 发现其为 devel/lib/Package_Name 下, 只有 catkin_make 后才能放进去, 顺序不对.
经调查发现如下传参方式

参数接口

通过 Main 函数传入

ros::init 的时候传入到 main 函数的 argv 中.

程序1:

1
2
3
4
5
6
7
8
9
10
11
12
int main(int argc, char** argv)
{
ros::init(argc, argv, "node_name");
if(argc > 1)
{
for(int i=1; i<argc; i++)
{
std::cout<<"argv["<<i<<"] "<<argv[i]<<std::endl;
}
}
return 0;
}

通过参数服务器传入

同时参数服务器又分为全局命名空间与私有命名空间, 作用于不同的范围内. 其中注意私有命名空间使用的 NodeHandle 初始化时需要加上 "~" 参数表明私有.

程序2:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
int main(int argc, char** argv)
{
ros::init(argc, argv, "node_name");
//全局命名空间
ros::NodeHandle n;
std::string n_arg;
n.param<std::string>("n_arg",n_arg,"default_n_arg_value");
std::cout<<"n_arg="<<n_arg<<std::endl;
//私有命名空间
std::string pn_arg;
ros::NodeHandle pn("~");
pn.param<std::string>("pn_arg",pn_arg,"default_pn_arg_value");
std::cout<<"pn_arg="<<pn_arg<<std::endl;
return 0;
}

传入方式

rosrun 命令后添加

例如程序1:

输入

1
rosrun pkg_name node_name arg1 arg2

输出

1
2
argv[1] arg1
argv[2] arg2

程序2:

输入, 注意, 私有参数的 _ 代替

1
rosrun _pn_arg:=aaa

输出

1
2
n_arg=default_arg1
pn_arg=aaa

下面介绍的 argument 也可以类似地在 rosrun 后添加.

launch file 传入

node 的属性 args

对于 main 函数的参数可以直接在 node 的属性 args 里添加. 对于程序 1, 传入 2 个参数 a1 a2.

1
2
3
<launch>
<node pkg="pkg_name" type="param_test" name="pkg_name" args="a1 a2" output="screen"/>
</launch>

也可以通过 argument(后面介绍)和 parameter 传入.

argument

如下 my_argument 的默认参数是 b1 b2, 2 个参数.

1
2
3
4
<launch>
<arg name="my_argument" default="b1 b2"/>
<node pkg="pkg_name" type="param_test" name="pkg_name" args="$(arg my_argument)" output="screen"/>
</launch>

如果想要修改默认参数可以在启动 launch 的时候修改, 如下:

1
roslaunch pkg_name launch_file_name.launch my_argument:="b3 b4"

parameter

对于程序 2, 如下设置. 全局参数使用 argument 传参, 私有参数直接赋值.

1
2
3
4
5
6
7
<launch>
<arg name="argument1" default="argument1_value" />
<param name="n_arg" value="$(arg argument1)" />
<node pkg="pkg_name" type="param_test" name="pkg_name" output="screen">
<param name="pn_arg" value="pn_arg_value"/>
</node>
</launch>

寻找 pkg 相对路径

$(find pkg) 的值赋给 argumentparameter, 得到 roscd pkg 的路径.

1
2
3
<launch>
<param name="value" value="$(find pkg)/scripts/test.py"/>
</launch>

argumentparameter 的区别

尽管 argumentparameter 的中文意思有时可互换, 但他们在 ROS 中的意义完全不同.
存在 parameter server 上, nodes 可通过 ros::param::get 函数编程得到, 用户可通过 rosparam 获取. 与之不同, argument 仅在 launch 文件内部有意义, nodes 不能直接获取它们的值.

argument 在 launch file 之间的传递

父 launch file 中:

1
2
3
4
5
6
7
<include file="path_to_file">

<arg name="argument_name" value="argument_value"/>

......

</include>

子 launch file 中:

1
<arg name="argument_name" value="$(arg argument_name)"/>

参考链接

https://www.jianshu.com/p/02ee8f513295
https://blog.csdn.net/DoctorChen618/article/details/84150623

作者

cx

发布于

2021-08-04

更新于

2022-11-04

许可协议