#ifndef _SHAREDPOINTER #define _SHAREDPOINTER template class SharedPointer { T* value; unsigned* instances; void free(); void copyFrom(const SharedPointer& other); public: SharedPointer(T* value); SharedPointer(); ~SharedPointer(); SharedPointer(const SharedPointer& other); SharedPointer& operator=(const SharedPointer& other); SharedPointer(SharedPointer&& other); SharedPointer& operator=(SharedPointer&& other); T& operator*(); const T& operator*() const; T* operator->(); const T* operator->() const; unsigned RefCount() const; }; template void SharedPointer::free() { if (instances == nullptr) return; --*instances; if (*instances == 0) { delete instances; delete value; } } template void SharedPointer::copyFrom(const SharedPointer& other) { this->instances = other.instances; this->value = other.value; ++*instances; } template SharedPointer::SharedPointer(T* value) : instances(new unsigned), value(value) { *instances = 1; } template SharedPointer::SharedPointer() : instances(), value() { } template SharedPointer::~SharedPointer() { free(); } template SharedPointer::SharedPointer(const SharedPointer& other) { copyFrom(other); } template SharedPointer& SharedPointer::operator=(const SharedPointer& other) { if (this != &other) { free(); copyFrom(other); } return *this; } template SharedPointer::SharedPointer(SharedPointer&& other) { instances = other.instances; value = other.value; other.instances = nullptr; other.value = nullptr; } template SharedPointer& SharedPointer::operator=(SharedPointer&& other) { if (this != &other) { free(); instances = other.instances; value = other.value; other.instances = nullptr; other.value = nullptr; } return *this; } template T& SharedPointer::operator*() { return *value; } template const T& SharedPointer::operator*() const { return *value; } template T* SharedPointer::operator->() { return value; } template const T* SharedPointer::operator->() const { return value; } template unsigned SharedPointer::RefCount() const { if (instances == nullptr) return 0; return *instances; } #endif /* _SHAREDPOINTER */