#include <iostream>
struct Base
{
    virtual void Serialize(std::ostream &os) const
    {
        os << "Base";
    }
};

struct Derived : Base
{
    virtual void Serialize(std::ostream &os) const override
    {
        os << "Derived, ";
        Base::Serialize(os);
    }
};

//...

std::ostream &operator<<(std::ostream &os, Base const &b)
{
    b.Serialize(os);
    return os;
}

//...

int main()
{
    Base b;
    Derived d;
    Base &bd = d;
    std::cout << b << std::endl;
    std::cout << d << std::endl;
    std::cout << bd << std::endl;
}
