2015-12-14 6 views
0

У меня есть класс object_handler, который заботится о том, чтобы обрабатывать объекты, хранящиеся в его векторе.Удаление объекта через обработчик объекта

class object_handler { 
    private: 
     std::vector<object*> m_objects; 
     // ... 

    public: 
     void add(object* x_object); 
     void remove(object* x_object); 
     void update(); 
     void render(); 
     // ... 
    }; 

Класс объекта является основным объектом я хотел бы использовать в своей игре и что теперь мне нужно сделать для того, чтобы иметь возможности удалить себя, когда это необходимо (например, когда это здоровье опускается ниже нуля). Один из способов, с которым я думал, что это сработает, - это если я дал объектам указатель на их обработчик, чтобы они могли получить доступ к функции удаления обработчика, но это оказалось катастрофой: компилятор начал бросать странные ошибки (например, «ожидаемый»; до * в "object_handler * m_handler" "), я думаю, это потому, что они включают друг друга.

Что было бы правильным способом хранить игровые объекты и обрабатывать их удаление? Было бы очень полезно, если бы объект мог удалять себя, когда он волновал вектор.

Еще один способ, которым я бы работал, если бы объект удалил сам, и вектор столкнется с пустым указателем и удалит его, но я не знаю, насколько это хорошо.

+0

Возможно, ваши «странные ошибки» были решены с помощью прямого объявления. Что касается «правильного способа хранения игровых объектов и обработки их удаления», это полностью зависит от вас. Для такого рода вещей нет «правильного пути» или «неправильного пути». –

+0

Осторожно удалять чужие данные. Если объект удаляется из вектора, в то время как обработчик объекта выполняет итерацию, результаты не будут хорошими. Вероятно, лучше иметь метод «RemoveMe» или аналогично уведомлять «object_handler» о том, что объект можно удалить, когда это безопасно. – user4581301

ответ

0

Ошибка, которую вы описываете, звучит так, как будто вы можете использовать форвардные объявления, а не полные. Это позволит вам иметь класс object_handler, а ваш класс object ссылаются друг на друга по ссылкам или указателям в своем интерфейсе, определенном в файлах заголовков. Фактическое полное включение только тогда должно быть включено в файлы реализации (.cpp), и порядок включения в действительности не имеет значения. Например:

Файл object_handler.h:

#include <vector> 

// NOTE: No #include here for object class, 
//  only a forward reference 

class object; 

class object_handler { 
private: 
    std::vector<object*> m_objects; 
    // ... 

public: 
    void add(object* x_object); 
    void remove(object* x_object); 
    void update(); 
    void render(); 
    // ... 
}; 

Файл object.h:

// NOTE: No #include here for object_handler class, 
//  only a forward reference 

class object_handler; 

class object { 
public: 
    object(object_handler& handler); 
    ~object(); 

private: 
    object_handler& m_handler; 
}; 

Файл object.cpp:

// NOTE: #include both headers, order doesn't matter 

#include "object.h" 
#include "object_handler.h" 

object::object(object_handler& handler) : 
    m_handler(handler) 
{ 
    m_handler.add(*this); 
} 
object::~object() 
{ 
    m_handler.remove(*this); 
} 

ли это подходящий способ управления object экземпляров будет зависеть на остальной части вашего кода. Вышеприведенный подход не является чем-то необычным. Возможно, вам захочется изучить примеры, такие как иерархия Qt QObject, которая имеет аналогичные классы для вас (например, QObjectCleanupHandler).

1

Обычно я использую флаг removed (true или false) внутри класса Entity. Там я могу удалить их в основном цикле.

Ваш пример с удалением объекта тоже должен быть в порядке, так как вы можете переслать объявление, чтобы класс прерывал циклическое включение. Но я бы не рекомендовал это, поскольку это делает, когда и где ваши объекты удалены неясно.

+0

Я отредактировал ответ, скажите, если что-то добавить снова. Благодарю. –

+0

Сделано быстрое исправление опечатки и настройка грамматики. – user4581301

Смежные вопросы