<每日修行>第一期::typename

博主在研究随机SLAM算法时遇到代码中typedef与typename的使用问题。文章详细解析了typedef的作用,以及typename在模板类中的必要性。重点在于理解Odometry2d::TInput的定义和为何采用typedef声明。

前言

每日修行是2021年4月22日开设的系列博客,记录了作者本人每日学习所遇到的问题及解决方法,由于作者本人知识储备量有限,故所思所想未必正确,有不当之处还请指正。

问题

今天在看随机slam算法的一个C++开源代码,但遇到了相当多的问题,话不多说,先上程序。`

  void generateTrajectory(int randSeed = 0){

    srand48( randSeed);

    TimeStamp t;
    int seg = 0;
    MotionModel_Odometry2d::TState::Mat Q;
    Q << vardx_, 0, 0, 0, vardy_, 0, 0, 0, vardz_;
    MotionModel_Odometry2d motionModel(Q);
    MotionModel_Odometry2d::TInput input_k(t);			
    MotionModel_Odometry2d::TState pose_k(t);
    MotionModel_Odometry2d::TState pose_km(t);
    groundtruth_displacement_.reserve( kMax_ );
    groundtruth_pose_.reserve( kMax_ );				
    groundtruth_displacement_.push_back(input_k);
    groundtruth_pose_.push_back(pose_k);
    ...

这段代码用于产生仿真用的轨迹,而input_k是产生轨迹的重要参数,我注意到它是由MotionModel_Odometry2d::TInput类定义,于是我开始在一堆头文件里翻找该类的声明,

class MotionModel_Odometry2d : public ProcessModel< Pose2d, Odometry2d >
{
public:

  /** Default constructor */
  MotionModel_Odometry2d();

  /** Constructor with process noise input 
   * \param Q additive zero-mean white Gaussian noise covariance matrix
   */
  MotionModel_Odometry2d( Pose2d::Mat &Q );

  /** Default destructor */
  ~MotionModel_Odometry2d();
 ...

结果在该类的声明头文件里并没有发现TInput的声明,可见答案只有一个那就是TInput必然是在它继承的公有制对象中,于是我又去寻找基类Processmodel的声明,终于在该类的声明头文件里找到了TInput的相关声明,代码如下。

template<class StateType, class InputType>
class ProcessModel
{
public:

  EIGEN_MAKE_ALIGNED_OPERATOR_NEW;

  typedef StateType TState;
  typedef InputType TInput;

  /** Default constructor */
  ProcessModel():
    inputNoiseDefined_(false)
  {}

  /** 
   * Constructor 
   * \param[in] Q covariance for the additive zero mean white Gaussian noise for this model 
   */
  ProcessModel(typename StateType::Mat &Q){
    setNoise(Q);
  }
...

这段代码让我感到困惑的有两个点,第一个点是TInput为什么要用typedef定义别名的方式来声明,与其在这里定义别名为什么不直接在类模板参数上修改?第二点是typename的使用问题,这里为什么要用typename?

解决方法

typename的用法有多种,我一开始知道的就是typename是class的同义词,常用于模板中指示参数如:

template <typename T1,typename T2>
function(T1,T2){}

后来网上查过后才知道原来typename还有一个非常重要的用法,那就是指示类型。就以这段代码来说

ProcessModel(typename StateType::Mat &Q){
    setNoise(Q);
  }

模板实例化之前是不知道Mat是参数变量还是类型的, 所以运行就会报错,故需要提前使用typename指示Mat为类型,编译才能顺利通过。
最后即就是一开始寻找的TInput的声明,虽然不知道为什么要用typedef,但至少从类模板的实例化上来看

class MotionModel_Odometry2d : public ProcessModel< Pose2d, Odometry2d >

TInput是Odometry2d类型,具体包括哪些内容需要去包含Odometry2d声明的头文件与源文件中看了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值