Question

Good day,

considering the following code, could one classify prototypical OOP to be a paradigm in

C++?

#include <iostream>

template< class... Bases >
struct TestClass : public Bases...
{
    int a;
    template< class... Parents >
    TestClass< Parents... >* Create() {
        return new TestClass< Parents... >();
    }
    TestClass< Bases... >* Create() {
        return new TestClass< Bases... >();
    }
};
struct Foo {
    int fizz;
};
struct Bar {
    int buzz;
};
int main()
{
    TestClass< Foo > a;
    a.a = 10;
    a.fizz = 20;
    std::cerr << a.fizz << "\n";
    std::cerr << a.a << "\n";
    auto b = a.Create();
    b->fizz = 30;
    std::cerr << b->fizz << "\n";
    auto c = b->Create< Bar >();
    c->buzz = 357;
    std::cerr << c->buzz << "\n";
    auto d = b->Create< Foo, Bar >();
    d->fizz = 0;
    d->buzz = 1;
    std::cerr << d->fizz << "\n";
    std::cerr << d->buzz << "\n";
    return 0;
}

FYI, I forgot to manage my memory, sorry!

Was it helpful?

Solution

No, I don't think so. The key difference between "prototypical" and "classical" OO is that prototypical OO doesn't have classes: the prototype is itself an object. If the prototype is modified, all objects "inheriting" from it follow suit. In this example, that is not the case.

OTHER TIPS

I can't help but notice a lot of confusion.

  1. The member function template 'Create' doesn't actually

    • have anything to with a TestClass instance (should be static)
    • have anything to with the containing TestClass's template arguments (should be a namespace function, not a member of the class template)
  2. the non-generic Create method should use the 'injected' type name instead of spelling the template args out needlessly

  3. there is no polymorphic use, so don't unnecessary dynamic allocations or raw pointers (this also solves the problem with memory cleanup)

  4. minor nit: try to use less confusing names and formatting in examples

Here's my equivalent:

template< class... Bases >
struct TestClass : public Bases... {
    int testfield;
    TestClass Create() {
        return TestClass();
    }
};

template< class... Parents >
static TestClass< Parents... > CreateTestClass() {
    return TestClass<Parents... >();
}

struct Fizzer {
    int fizz;
};
struct Buzzer {
    int buzz;
};
int main()
{
    TestClass< Fizzer > fizzer;
    fizzer.testfield = 10;
    fizzer.fizz = 20;

    auto b = fizzer.Create();
    b.fizz = 30;

    auto c = CreateTestClass< Buzzer >();
    c.buzz = 357;

    auto d = CreateTestClass< Fizzer, Buzzer >();
    d.fizz = 0;
    d.buzz = 1;
}

And, NO, I don't think this code is 'idiomatic' for much. I haven't seen it (although it might resemble a straightforward implementation of a tuple-like class. That's not idiomatic, anyway: idiomatic would be to not write such a class, but to compose std::tuple (boost has several flavours with extensions)

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top