将虚拟类引用作为参数传递给构造函数

Passing a virtual class reference as an argument to constructor

本文关键字:参数传递 构造函数 虚拟 引用      更新时间:2023-10-16

我在.h文件中定义了一个抽象类Algorithm1。我希望这个抽象类Algorithm1能够保存对其他一些抽象类的引用,并能够在运行时确定具体的引用。因此,我的Algorithm1包含这些引用,我希望能够通过构造函数传递确切的实现。Algorithm1的一个确切实现是类Algorithm1A

算法1.h

#include "Interval.h"
#include "OrderedAlphabet.hpp"
#include "Rank.h"
//! Algorithm1 interface
class Algorithm1 {
protected:
    Rank &rank;
    OrderedAlphabet &alphabet;
    std::map<symbol_type, occurence_type> &C; 
public:
    Algorithm1(Rank &r,
               OrderedAlphabet &a,
               std::map<symbol_type, occurence_type> &c):
                rank(r), alphabet(a), C(c) {
    }
};
#endif /* Algorithm1_h */

算法1A

#include "Algorithm1.h"
class Algorithm1A : Algorithm1 {
    std::string uniqueCharsInInterval(int i, int j) {
        rank.rank() // dome something with ABSTRACT rank
    }

    std::vector<Interval> getIntervals(int i, int j) {
        alphabet.getSize() // do something with alphabet - not abstract
        C.find('x') // do something with C - not abstract
    }
};

除此之外,我的Rank类也是一个抽象类,但由WTRankNTRank等类实现。所以我真正想要的是能够传递WTRank对象,但作为RankAlgorithm1构造函数的引用。

Rank.h

#ifndef Rank_h
#define Rank_h
#include "DataTypes.h"
//! Rank interface
class Rank {
public:
    virtual unsigned long long rank(int index, symbol_type symbol)=0;
};
#endif /* Rank_h */

我的WTRank类被划分为.h.cpp文件。

WTRank.h

#ifndef WTRank_h
#define WTRank_h
#include "Rank.h"
#include <sdsl/wavelet_trees.hpp>
using namespace sdsl;
//! Rank based on Wavelet Tree
class WTRank: public Rank {
private:
    wt_huff<> wt;
public:
    WTRank(wt_huff<> w_tree) {
        this->wt = w_tree;
    }
    ~WTRank();
    unsigned long long rank(int index, symbol_type symbol);
};
#endif /* WTRank_h */

WTRank.cpp

#include "WTRank.h"
unsigned long long WTRank::rank(int index, symbol_type symbol) {
    return wt.rank(index, symbol);
}

现在,如果我想创建一个实现Algorithm1抽象类的Algorithm1A对象,并且我想给它的构造函数提供所需的参数,我正在做这样的事情——并得到"No matching constructor error"

wt_huff<> wt;
construct_im(wt, str, 1);
OrderedAlphabet alphabet(10);
std::map<symbol_type, occurence_type> C = calculateC(wt, alphabet);
WTRank wtrank = *new WTRank(wt);
Algorithm1A alg = new Algorithm1A(wtrank, &alphabet, &C); // ERROR!!

为了让它发挥作用,应该如何做到这一点?

构造函数在C++中默认不继承。如果您有C++11,您可以显式地将基类构造函数转发到派生类:

class Algorithm1A : Algorithm1 {
public:
  using Algorithm1::Algorithm1;
  ...
};

构造函数不是继承的。您需要在Algorithm1A上定义一个构造函数,该构造函数采用适当的参数。

Algorithm1A::Algorithm1A(Rank &r,
                         OrderedAlphabet &a,
                         std::map<symbol_type, occurence_type> &c):
  Algorithm1(r, a, c)
{}