Opinions ?

The Partridge Family were neither partridges nor a family. Discuss.
Post Reply
MrGodin
Posts: 721
Joined: November 30th, 2013, 7:40 pm
Location: Merville, British Columbia Canada

Opinions ?

Post by MrGodin » October 2nd, 2017, 4:39 am

I am trying to create an ObjectManager using templates. This works, but is it at all reasonable ?
Just fishing for input

Code: Select all

#pragma once


#include "GameObject.h"
class ObjectManager
{
	
	//hold class type in map (std::type_index) then have a container
	// to hold all the object of std::type_index.
	std::unordered_map<std::type_index, std::vector<std::unique_ptr<GameObject>>> m_objects;
public:
	ObjectManager() = default;
	~ObjectManager() {}
	template<typename Obj>
	size_t GetNumbObjects()
	{
		std::type_index index(typeid(Obj));
		return m_objects[index].size();
	}
	template<typename Obj>// incoming class
	Obj& AddObj(DataPack& data)
	{
		std::type_index index(typeid(Obj));// class type
		// DataPack is a base struct
		// the Obj then type casts to proper DataPack in 
		// it's constructor ie: DromeDataPack* pack = (DroneDataPack*)data
		m_objects[index].push_back(std::make_unique<Obj>(&data));
		// GameObject friends this class to hold it's index (mgr_index is a private member)
		m_objects[index].back()->mgr_index = m_objects[index].size() - 1;
		return static_cast<Obj&>(*m_objects[index].back());

	}
	template<typename Obj>
	Obj& GetObj(int in_index)
	{
		Obj* empty = nullptr;// cheezy way to send a nullptr ??
		std::type_index index(typeid(Obj));
		assert(m_objects.count(index) != 0);// make sure the class type is here
		if (in_index < 0 || in_index >= m_objects[index].size())
			return *empty;
		return static_cast<Obj&>(*m_objects[index][in_index]);
	}
	template<typename Obj>
	void RemoveObj(Obj* object)// won't compile is classes are different
	{
		std::type_index index(typeid(Obj));
		assert(m_objects.count(index) != 0);
		int I = object->mgr_index;
		if( I < 0 || I >= m_objects[index].size())
			return;
		m_objects[index][I].reset();
		m_objects[index].erase(m_objects[index].begin() + I);
				
	}
};
Curiosity killed the cat, satisfaction brought him back

albinopapa
Posts: 4373
Joined: February 28th, 2013, 3:23 am
Location: Oklahoma, United States

Re: Opinions ?

Post by albinopapa » October 2nd, 2017, 6:19 am

Code: Select all

   Obj& GetObj(int in_index)
   {
      Obj* empty = nullptr;// cheezy way to send a nullptr ??
      std::type_index index(typeid(Obj));
      assert(m_objects.count(index) != 0);// make sure the class type is here
      if (in_index < 0 || in_index >= m_objects[index].size())
         return *empty;
      return static_cast<Obj&>(*m_objects[index][in_index]);
   }
In these cases, can't wait for std::optional or whatever it's called. Of course dereferencing a nullptr is a bad thing, but I guess that is why you have the assert there.

In these cases, I usually have two functions, one that checks if item is in list and if in list, call second function to get item, if not then do something else.
bool IsInMap(int in_index ) const;
const Obj& GetObj()const;
Obj& GetObj();

Ok, three functions, one const and one non const getter and a checker.

Not saying it's optimal, but it's a way of dealing with trying to return references instead of pointers. The other option would be to create a struct that simulates an optional.

Code: Select all

template<class T>
class Optional
{
public:
     explicit Optional()=default;
     explicit Optional( T& Data )
          :
     data(&Data),
     isValid(true)
     {}

     operator bool()const
     {
          return data != nullptr;
     }
     T& Get()
     {
          return *data;
     }
private:
     T* data = nullptr;
};
Something like that, not sure it will work, not tested. If the value you want is there, you create the Optional object with the data and return the optional object. If the data is not there, you return a default constructed Optional object which has a nullptr as default. When you return from the GetObj function, you test the optional object return just as you would a pointer.

Code: Select all

auto option = GetObj(int in_index);
if(option)
{
}
else
{
}
I don't know what kind of performance hit RTTI (RunTime Type Information) will cause on your project either. In the end, you'll have to decide what works for you.
If you think paging some data from disk into RAM is slow, try paging it into a simian cerebrum over a pair of optical nerves. - gameprogrammingpatterns.com

MrGodin
Posts: 721
Joined: November 30th, 2013, 7:40 pm
Location: Merville, British Columbia Canada

Re: Opinions ?

Post by MrGodin » October 2nd, 2017, 1:10 pm

@albinopapa .. hmm i wonder if a predicate or lamnda might do the trick. I'll fiddle fuck around with it but i have since made some additional changes and I'm liking what i've done. Thanks for the input.
Curiosity killed the cat, satisfaction brought him back

MrGodin
Posts: 721
Joined: November 30th, 2013, 7:40 pm
Location: Merville, British Columbia Canada

Re: Opinions ?

Post by MrGodin » October 4th, 2017, 1:25 am

from what i understand with further reading is that using RTTI is the same expense as using classes with virtual functions as there is a lookup table associated with virtual functions. I'm not all that concerned atm ;)
Curiosity killed the cat, satisfaction brought him back

albinopapa
Posts: 4373
Joined: February 28th, 2013, 3:23 am
Location: Oklahoma, United States

Re: Opinions ?

Post by albinopapa » October 4th, 2017, 2:51 am

nice to know
If you think paging some data from disk into RAM is slow, try paging it into a simian cerebrum over a pair of optical nerves. - gameprogrammingpatterns.com

User avatar
chili
Site Admin
Posts: 3948
Joined: December 31st, 2011, 4:53 pm
Location: Japan
Contact:

Re: Opinions ?

Post by chili » October 5th, 2017, 4:19 am

I would say what you've got there is fine, but std::shared_ptr would be better. It handles references that are added without involvement of the manager, and it is thread-safe. I generally prefer to go for a std solution if one exists; it makes for more idiomatic code.
Chili

MrGodin
Posts: 721
Joined: November 30th, 2013, 7:40 pm
Location: Merville, British Columbia Canada

Re: Opinions ?

Post by MrGodin » October 6th, 2017, 1:03 am

Well i have found flaws in it. The object holds it's index in the container but i failed to update the remaining objects index when removing one from the vector... back to the drawing board ..
Curiosity killed the cat, satisfaction brought him back

Post Reply