Ошибка компоновщика C ++ при наследовании из класса шаблона - PullRequest
1 голос
/ 18 марта 2020

При компиляции моего кода (вы увидите, почему этот большой, а не фрагмент MRE позже)

    template<typename Elem>
    class base_stream
    {
    protected:
        array_list<Elem>* buffer_ = nullptr; // array_list is my class, it works
    public:
        virtual void open() = 0;
        virtual void close() = 0;
    };
    template<typename Elem>
    class base_input_stream : public base_stream<Elem>
    {
    public:
        void open() override
        {
            this->buffer_ = new array_list<Elem>;           
        }
        void close() override
        {
            this->buffer_ = nullptr;
        }
        Elem* read_until(Elem terminator)
        {
            Elem e;
            while((e = read()) != terminator) this->buffer_->add(e);
            return this->buffer_->as_array();
        }
        virtual Elem read();
    };
    class input_stream : public base_input_stream<char>
    {
    private:
        FILE* file_;
    public:
        input_stream(FILE* f)
        {
            file(f);
            open();
        }
        input_stream() { open(); }
        ~input_stream()
        {
            close();
            delete buffer_;
        }
        char* read_line()
        {
            return this->read_until('\n');
            // the problem is here, when I remove read_line, everything works.
        }
        char read() override
        {
            return fgetc(file_);
        }

        void file(FILE* f)
        {
            file_ = f;
        }  
};

и файл cpp

msl::input_stream is(stdin);
msl::stdos.write("Hello, ");
msl::stdos.write(is.read_line());

(пожалуйста, не судите меня за то, что я делаю ...)

эта ошибка появляется:

Undefined symbols for architecture x86_64:
  "msl::base_input_stream<char>::read()", referenced from:
      vtable for msl::base_input_stream<char> in msl-test-9638bd.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

но (странно) это работает:

#include <iostream>

template<typename E>
class X
{

};

template<typename E>
class Y : public X<E>
{
public:
    void doStuff(E foo)
    {
        std::cout << foo << std::endl;
    }
};

class Z : public Y<char>
{
public:
    void hmm() {
        doStuff('h');
        // or Y<char>::doStuff('h');
        // or this->doStuff('h');
    }
};

Z hmm = Z();

и компилируется без ошибок. (результат, как и ожидалось h)

В чем здесь проблема. Ошибка странная, потому что другие методы работают и только read_line не

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...