Abstract object cannot declare

I have a problem with abstract / virtual classes, replication of the problem here:

#include <iostream>

class A
{
protected:
    virtual std::string getDateTime() = 0;
    virtual void Write(std::string data, bool addDate) = 0;
    virtual bool CheckFile() = 0;
    virtual bool OpenFile(std::string path) = 0;
    virtual void CloseFile() = 0;
};

class B
    : public A
{
public:
    virtual std::string ToString() { return ""; };
    virtual void Write(std::string data) { };
};

class C
    : public A
{
protected:
    std::string getDateTime()
    {
        return "TODAY";
    };

    void Write(std::string data, bool addDate)
    {
        std::cout << "BasicClassA Write" << std::endl;
    };

    bool CheckFile()
    {
        std::cout << "BasicClassA CheckFile" << std::endl;
        return true;
    };

    bool OpenFile(std::string path)
    {
        std::cout << "BasicClassA OpenFile" << std::endl;
        return true;
    };

    void CloseFile()
    {
        std::cout << "BasicClassA CloseFile" << std::endl;
    };
};

class D
    : public B,
      public C
{
public:
    BasicClassB();
    virtual ~BasicClassB();

    std::string ToString()
    {
        return "BasicClassB tostring";
    };

    void Write(std::string data)
    {
        std::cout << "BasicClassB Write" << std::endl;
    };
};

int main(int ac, char *av[])
{
    BasicClassB b;
    std::cout << b.ToString() << std::endl;
    b.Write("");
    return 0;
}

This has a compilation error:

../src/main.cpp: 'int main (int, char **):
.. /src/main.cpp:82: error: 'b ' BasicClassB
.. /src/main.cpp:64: : "BasicClassB" :
.. /src/main.cpp:13: note: virtual std::string BaseClassA:: getDateTime()
.. /src/main.cpp:14: note: virtual void BaseClassA:: Write (std::string, bool)
.. /src/main.cpp:15: note: virtual bool BaseClassA:: CheckFile()
.. /src/main.cpp:16: note: virtual bool BaseClassA:: OpenFile (std::string)
.. /src/main.cpp:17: note: virtual void BaseClassA:: CloseFile()

, , BaseClassA ( BasicClassA) , BasicClassB BasicClassA, ?

? , ?

[ ] I updated the class names as suggested by the comment
: A .

, - , , , , , ...

, "" , , , overriden ( )

,   class Any: public virtual Anyother {} (). , , ?

+3
4

++. , ++ : BasicClassA BaseClassB BaseClassA ( vtable ).

, Virtual Inheritance.

:

#include <iostream>


class A
{
    public:
        A(int x) {m_a = x;}
        virtual ~A() {}
        int m_a;
        virtual int getA() {return m_a;}
};

class B : public A
{
    public:
        B() : A(1) {}
};

class C : public A
{
    public:
        C() : A(2) {}
};

class D : public B,
          public C
{
};

void useB(B* b)
{
    std::cout << "useB:" << b->getA() << std::endl;
}

void useC(C* c)
{
    std::cout << "useC:" << c->getA() << std::endl;
}

int main()
{
    D* d = new D();
    useB(d);
    useC(d);

    return 0;
}

:

useB:1
useC:2

, .

#include <iostream>


class A
{
    public:
        A(int x) {m_a = x;}
        virtual ~A() {}
        int m_a;
        virtual int getA() {return m_a;}
        virtual int virt() = 0;
};

class B : virtual public A
{
    public:
        B() : A(1) {}
};

class C : virtual public A
{
    public:
        C() : A(2) {}
        virtual int virt() {return 42;}
};

class D : public B,
          public C
{
    public:
        D() : A(3) {}
};



void useB(B* b)
{
    std::cout << "useB:" << b->getA() << std::endl;
}

void useC(C* c)
{
    std::cout << "useC:" << c->getA() << std::endl;
    std::cout << "useC-virt:" << c->virt() << std::endl;
}

int main()
{
    D* d = new D();
    useB(d);
    useC(d);

    return 0;
}

:

useB:3
useC:3
useC-virt:42

. C B m_a, D().

EDIT: :

#include <iostream>

class A
{
protected:
    virtual std::string getDateTime() = 0;
    virtual void Write(std::string data, bool addDate) = 0;
    virtual bool CheckFile() = 0;
    virtual bool OpenFile(std::string path) = 0;
    virtual void CloseFile() = 0;
};

class B
    : virtual public A
{
public:
    virtual std::string ToString() { return ""; };
    virtual void Write(std::string data) { };
};

class C
    : virtual public A
{
protected:
    std::string getDateTime()
    {
        return "TODAY";
    };

    void Write(std::string data, bool addDate)
    {
        std::cout << "C Write" << std::endl;
    };

    bool CheckFile()
    {
        std::cout << "C CheckFile" << std::endl;
        return true;
    };

    bool OpenFile(std::string path)
    {
        std::cout << "C OpenFile" << std::endl;
        return true;
    };

    void CloseFile()
    {
        std::cout << "C CloseFile" << std::endl;
    };
};

class D
    : public B,
      public C
{
public:
    std::string ToString()
    {
        return "D tostring";
    };

    void Write(std::string data)
    {
        std::cout << "D Write" << std::endl;
    };
};

int main(int ac, char *av[])
{
    D b;
    std::cout << b.ToString() << std::endl;
    b.Write("");
    return 0;
}
+4

BaseClassA 5 . - " ". ( ) , .

BaseClassB, 5 , BaseClassA. ( BaseClassB , , ).

+1

BasicClassB BaseClassA, , :

virtual std::string getDateTime() = 0;
virtual void Write(std::string data, bool addDate) = 0;
virtual bool CheckFile() = 0;
virtual bool OpenFile(std::string path) = 0;
virtual void CloseFile() = 0;

.

: BasicClassB, .

, Write BasicClassB:

virtual void Write(std::string data) { };

BaseClassA:

virtual void Write(std::string data, bool addDate) = 0;

, BasicClassB, .

+1

The fact that you add "= 0" to your functions means that they are purely virtual and must be implemented in child classes. This is obviously not what you want. If you drop "= 0" from functions that have an implementation in the base class, it should work as intended.

0
source

Source: https://habr.com/ru/post/1776223/


All Articles