nsf gamedevЖурнал

C++0x no comments

Автор:

Зачем это нужно? История умалчивает. Медитируйте. :)

#include <cstdio>
#include <cstdint>
#include <new>
#include <utility>

// class represents space for a type with manual construction and destruction
// (also can PODify any class, e.g. convert full featured Class to POD type)
template <typename T>
struct storage {
  template <typename ...Args>
  void construct(Args &&...args)  { new (buf) T(std::forward<Args>(args)...); }

  void destruct() { get()->~T(); }

  T *operator->() { return get(); }
  T &operator*() { return *get(); }

  T *get() { return reinterpret_cast<T*>(buf); }

  uint8_t buf[sizeof(T)];
};

struct WeirdClassWithLotsOfData {
  // have no default constructor
  WeirdClassWithLotsOfData(int a, int b, int c): a(a), b(b), c(c)
  {
    for (size_t i = 0; i < 100; ++i)
      d[i] = i;
    printf("Weird class constructed: %d %d %d\n", a, b, c);
  }

  ~WeirdClassWithLotsOfData()
  {
    printf("Weird class destroyed: %d %d %d\n", a, b, c);
  }

  void say_hello()
  {
    printf("Hello: %d %d %d\n", a, b, c);
  }

  int a, b, c;
  int d[100];
};

// allocate space for all data in one malloc
struct PackOfWeirdness {
  storage<WeirdClassWithLotsOfData> objects[5];

  PackOfWeirdness()
  {
    // do weird initialization
    for (int i = 4; i >= 0; --i)
      objects[i].construct(i+1, i+2, i+3);
  }

  ~PackOfWeirdness()
  {
    for (size_t i = 0; i < 5; ++i)
      objects[i].destruct();
  }

  void reinit()
  {
    for (size_t i = 0; i < 5; ++i) {
      objects[i].destruct();
      objects[i].construct(i+1, i*i, i*i*i);
    }
  }
};

int main(int argc, char **argv)
{
  printf("Before pack of weirdness\n");
  {
    auto pack = new PackOfWeirdness;
    for (size_t i = 0; i < 5; ++i)
      pack->objects[i]->say_hello();
    pack->reinit();
    delete pack;
  }
  printf("After pack of weirdness\n");
  return 0;
}

27 мая 2010