【机器人学】机器人开源项目KDL源码学习:(5)KDL如何求解几何雅克比矩阵
来源:互联网 发布:唐勇的seo分享平台 编辑:程序博客网 时间:2024/05/22 00:53
这篇文章试图说清楚两件事:(1)几何雅克比矩阵的本质;(2)KDL如何巧妙地求解几何雅克比矩阵。
机器人的关节空间的速度可以映射到执行器末端在操作空间的速度,这种映射可以通过一个矩阵来描述,就是几何雅克比矩阵,了解雅克比矩阵需要了解这种映射关系的本质,否则在编写机器人运动学算法的时候会无从下手。
机器人执行器末端的速度v和角速度w和角速度的关系可以用下式表示:
(1)
把上式写成:
(2)
为什么要整理成(2)式呢?因为机械臂末端的速度可以认为是各个关节的运动导致末端的速度的叠加之后的效果。
所以,(2)式中等号后的每一列((3)式)就代表第i个关节对末端的造成的线速度和角速度。
(3)
现在介绍KDL中如何逐列的求雅克比矩阵,理解下边的内容需要回顾一下刚体运动的知识,刚体内任一点的速度等于基点的速度与该点随刚体绕基点转动速度的和,角速度一样。
如果有同学看过我的上一篇博客(【机器人学】机器人开源项目KDL源码学习:(2)牛顿拉普森迭代法求机器人的数值解)的话,应该明白我们的目的不是求机械臂末端的速度,而是在已知机械臂构型和每个关节角度位移的情况下,求解雅克比矩阵各项的值。
好的,在编程的时候,我们依然采用上边叙述的运动传递的思想,希望能够逐列地将雅克比矩阵求出来,明白了它的每一列表示什么意思,才能动手写代码,那它的每一列((4)式)代表什么意思呢?代表的是关节i在角速度为1的时候对机械臂最末端造成的速度!如果再乘以关节i的角速度的值,就得到了机械臂最末端的速度。从这个角度看(2)和(3)式就比较直观了,所有的关节对末端这也是KDL的巧妙之处。
(4)
有了这种理念,就可以看懂KDL中的求雅克比矩阵的代码了(orocos_kinematics_dynamics-master\orocos_kdl\src\chainjnttojacsolver.cpp)
形参q_in 表示机械臂在某一时刻的所有关节角位移,jac用来存放雅克比矩阵的值。
int ChainJntToJacSolver::JntToJac(const JntArray& q_in, Jacobian& jac, int seg_nr) { unsigned int segmentNr; if(seg_nr<0) segmentNr=chain.getNrOfSegments(); else segmentNr = seg_nr; //Initialize Jacobian to zero since only segmentNr colunns are computed SetToZero(jac) ; if( q_in.rows()!=chain.getNrOfJoints() || jac.columns() != chain.getNrOfJoints()) return (error = E_SIZE_MISMATCH); else if(segmentNr>chain.getNrOfSegments()) return (error = E_OUT_OF_RANGE); T_tmp = Frame::Identity(); SetToZero(t_tmp); int j=0; int k=0; Frame total; for (unsigned int i=0;i<segmentNr;i++) { //Calculate new Frame_base_ee if(chain.getSegment(i).getJoint().getType()!=Joint::None){ //pose of the new end-point expressed in the base total = T_tmp*chain.getSegment(i).pose(q_in(j)); //changing base of new segment's twist to base frame if it is not locked //t_tmp = T_tmp.M*chain.getSegment(i).twist(1.0); if(!locked_joints_[j]) t_tmp = T_tmp.M*chain.getSegment(i).twist(q_in(j),1.0); }else{ total = T_tmp*chain.getSegment(i).pose(0.0); } //Changing Refpoint of all columns to new ee changeRefPoint(jac,total.p-T_tmp.p,jac); //Only increase jointnr if the segment has a joint if(chain.getSegment(i).getJoint().getType()!=Joint::None){ //Only put the twist inside if it is not locked if(!locked_joints_[j]) jac.setColumn(k++,t_tmp); j++; } T_tmp = total; } return (error = E_NOERROR); }}
关键代码详解:
total和T_tmp用来处理坐标变换。
total = T_tmp*chain.getSegment(i).pose(q_in(j));//表示第i个连杆末端在基座标中的表示
T_tmp = total;//这行在循环体的最后,表示第i个连杆的起点在基坐标中的表示
t_tmp = T_tmp.M*chain.getSegment(i).twist(q_in(j),1.0);//求的是第i个关节对第i个连杆末端的速度(在基座标中的表示),设关节i的角速度为1,
changeRefPoint(jac,total.p-T_tmp.p,jac);//将雅克比矩阵更新,第k列表示第k个关节角速度为1时对末端的造成的线速度和角速度
jac.setColumn(k++,t_tmp);//为雅克比矩阵添加新的一列(t_tmp)
- 【机器人学】机器人开源项目KDL源码学习:(5)KDL如何求解几何雅克比矩阵
- 【机器人学】机器人开源项目KDL源码学习:(8)KDL的精髓
- 【机器人学】机器人开源项目KDL源码学习:(4)examples中的CMakeList.txt文件解读
- 【机器人学】机器人开源项目KDL源码学习:(2)牛顿拉普森迭代法求机器人的数值解
- 【机器人学】机器人开源项目KDL源码学习:(1)下载源码并在ubuntu下运行geometry部分(旋转矩阵)
- 【机器人学】机器人开源项目KDL源码学习:(4)机械臂逆动力学的牛顿欧拉算法
- 【机器人学】机器人开源项目KDL源码学习:(3)机器人操作空间路径规划(Path Planning)和轨迹规划(Trajectory Planning)示例
- 【机器人学】机器人开源项目KDL源码学习:(6)笛卡尔空间轨迹规划、圆弧过渡、姿态插值、梯形速度、pathlength
- sfkasnlkfaslkdasjkldjas;kdl
- 雅克比矩阵(机器人)
- Robotic KDL library
- 机器人的雅克比矩阵
- KDL与Eigen数据转换
- 机器人学基础(一)——机器人几何结构分类及其自由度
- 关于morden c++ design中的kdl问题(singleton)的解决
- ROS错误 rospkg.common.ResourceNotFound: kdl
- 从URDF到KDL(C++&Python)
- 六自由度机器人Jacobian(雅克比)矩阵计算类
- 1089. Insert or Merge
- 算法笔记_028-字符串转换成整数(Java)
- 算法训练 2的次幂表示
- Ajax实现文件上传
- 动态树分治——模板整理
- 【机器人学】机器人开源项目KDL源码学习:(5)KDL如何求解几何雅克比矩阵
- Android 开发艺术探索 读书笔记2
- leetCode
- 程序员的自我修养
- 1090. Highest Price in Supply Chain
- ArrayList和LinkedList的区别
- 第三章 JAVA内存结构(3)
- 【BZOJ 1046】【HAOI 2007】上升序列
- mysql 5.5多实例部署