Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/git/25.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 具有指向模板基类的指针_C++_Templates_Polymorphism_Bitset - Fatal编程技术网

C++ 具有指向模板基类的指针

C++ 具有指向模板基类的指针,c++,templates,polymorphism,bitset,C++,Templates,Polymorphism,Bitset,在下面的代码中,我有一个名为IDecoder的接口,它应该由这里的任何解码器类DecoderA和DecoderB实现。IDecoder中有一个位集,因此我将IDecoder作为模板类,位集的大小在派生类中确定。我还得到了一个容器类,它应该包含一个指向IDecoder类的指针,但由于IDecoder不是一个完整类型,我添加了一个伪DecoderBase类,IDecoder从中继承: #include <iostream> #include <bitset> class D

在下面的代码中,我有一个名为IDecoder的接口,它应该由这里的任何解码器类DecoderA和DecoderB实现。IDecoder中有一个位集,因此我将IDecoder作为模板类,位集的大小在派生类中确定。我还得到了一个容器类,它应该包含一个指向IDecoder类的指针,但由于IDecoder不是一个完整类型,我添加了一个伪DecoderBase类,IDecoder从中继承:

#include <iostream>
#include <bitset>

class DecoderBase
{
public:
    DecoderBase(){}
    virtual ~DecoderBase(){}
};

template<size_t nb>
class IDecoder : public DecoderBase
{
public:
    IDecoder(){}
    virtual ~IDecoder(){}
    virtual std::bitset<nb> GetDecodedFields() = 0;
};

const int DecoderAMaxFields = 100;
const int DecoderBMaxFields = 200;

class DecoderA : public IDecoder<DecoderAMaxFields>
{
public:
    DecoderA(){}
    ~DecoderA(){}
    std::bitset<DecoderAMaxFields> GetDecodedFields()
    {
        std::bitset<DecoderAMaxFields> bits;
        // assume we've decoded fileds number 1 and 10 here
        bits[1] = 1;
        bits[10] = 1;
        return bits;
    }
};

class DecoderB : public IDecoder<DecoderBMaxFields>
{
public:
    DecoderB(){}
    ~DecoderB(){}
    std::bitset<DecoderBMaxFields> GetDecodedFields()
    {
        std::bitset<DecoderBMaxFields> bits;
        // assume we've decoded fileds number 11, 29, 110 & 142 here
        bits[11] = 1;
        bits[29] = 1;
        bits[110] = 1;
        bits[142] = 1;
        return bits;
    }
};

class Container
{
public:
    Container(){}
    virtual ~Container(){}
    void SetDecoder(DecoderBase* decoder)
    {
        mDecoder = decoder;
    }
    DecoderBase* GetDecoder()
    {
        return mDecoder;
    }
private:
    DecoderBase* mDecoder;
};

int main()
{
    Container container;
    container.SetDecoder(new DecoderA());
    ((DecoderA*)container.GetDecoder())->GetDecodedFields();
    return 0;
}
正如您所看到的,在调用GetDecodedFields之前,我必须将它转换为一个解码器,这与多态性的目的正好相反!如何修复此代码?我也考虑过使用boost::dynamic_位集,但我不想使用它,因为它比普通位集慢。

编辑:这个答案是对问题下的注释的补充

容器使用哪种解码器是运行时信息,而位集的大小必须在编译时声明。这两个概念不能一起工作。你应该考虑使用向量。 顺便说一句:std::bitset和std::bitset的类型是不同的。没有可以用作基类的类型std::bitset。模板不是这样工作的。所以DecoderBase无法知道要返回哪些类型。 在本例中,有关如何使用std::vector而不是固定大小的std::Bitset的示例:

#include <iostream>
#include <bitset>
#include <vector>

class DecoderBase
{
public:
    DecoderBase() {}
    virtual ~DecoderBase() {}
    virtual std::vector<bool> GetDecodedFields() = 0;
};

class DecoderA : public DecoderBase
{
public:
    DecoderA() {}
    ~DecoderA() {}
    std::vector<bool> GetDecodedFields()
    {
        // assume we've decoded fileds number 1 and 10 here
        std::vector<bool> bits(100, false);
        bits[1] = true;
        bits[10] = true;
        return bits;
    }
};

class DecoderB : public DecoderBase
{
public:
    DecoderB() {}
    ~DecoderB() {}
    std::vector<bool> GetDecodedFields()
    {
        // assume we've decoded fileds number 11, 29, 110 & 142 here
        std::vector<bool> bits(200, false);
        bits[11] = 1;
        bits[29] = 1;
        bits[110] = 1;
        bits[142] = 1;
        return bits;
    }
};

class Container
{
public:
    Container() {}
    virtual ~Container() {}
    void SetDecoder(DecoderBase* decoder)
    {
        mDecoder = decoder;
    }
    DecoderBase* GetDecoder()
    {
        return mDecoder;
    }
private:
    DecoderBase* mDecoder;
};

int main()
{
    Container container;
    container.SetDecoder(new DecoderA());
    container.GetDecoder()->GetDecodedFields();
    std::cout << container.GetDecoder()->GetDecodedFields().size() << std::endl;
    return 0;
}

这里的问题不是多态性

您正在使用一个异构容器

<>没有C++的构造来访问容器的元素而不使用强制转换。< /P>
干净的方法是对容器元素进行动态强制转换,以将元素强制转换为其各自的类型。

从功能上讲,您试图实现什么样的位集?容器使用什么样的解码器是运行时信息,而位集的大小必须在编译时声明。这两个概念不能一起工作。您应该考虑使用vector.BTW:std::bitset和std::bitset的类型是不同的。没有可以用作基类的类型std::bitset。模板不是这样工作的。所以DecoderBase无法知道您想要返回哪种类型。dynamic_位集不可避免地会稍微慢一点——但这对您的目的真的很重要吗?它看起来确实是解决您问题的最简单的方法。@bobah我需要这个位集来进行逐位操作,这样我就可以快速知道哪些字段已被解码。vector与std::bitset有一个非常不同的接口。@πάνταῥεῖ 是的。但是,如果解码器的位集大小不同,他试图用std::bitset做的是不可能的。你应该知道,。我没有看到这个。那么我不明白昨天的答案有什么问题。