shared_ptr требует полного типа; не может использовать его с lua_State*

Я пишу C++ / обертка ООП для Lua. Мой код:

class LuaState
{
     boost::shared_ptr L;

     LuaState(): L( luaL_newstate(), LuaState::CustomDeleter )
     {
     }
}

Проблемой является lua_State, неполный тип, и shared_ptr конструктор требует полного типа. И мне нужно безопасное совместное использование указателя. (Забавная вещь, в документах повышения говорится, что большинство функций не требует полного типа, но конструктора, требует, таким образом, нет никакого способа использовать его. http://www.boost.org/doc/libs/1_42_0/libs/smart_ptr/smart_ptr.htm)

Банка я могу решить это?Спасибо.

8
задан topright gamedev 12 March 2010 в 15:17
поделиться

3 ответа

Вы используете свой собственный удалитель, а это означает, что вам не обязательно иметь полный тип при построении. Единственное требование - чтобы CustomDeleter мог это обработать. (он может преобразовать переданный указатель в полный тип, например (например, из void * в CompleteType * ).

Предпосылкой полноты является то, что когда-то конструктор shared_ptr вызывается с помощью средства удаления по умолчанию, он создает экземпляр класса, который содержит строку delete p; - и для того, чтобы этот код был правильным, p не должен быть неполным. Деструктор вызовет этот код удаления косвенно, поэтому он не зависит от полноты типа.

Однако, если вы передадите свой собственный удалитель, требования вашего собственного удалителя будут применяться. Обязательно определите CustomDeleter после завершения lua_State .

4
ответ дан 5 December 2019 в 23:14
поделиться

Учитывая, что lua_State * не может быть клонирован, имеет ли смысл копирование объекта LuaState? Какова ожидаемая семантика копирования такого изначально некопируемого объекта?

Похоже, вам нужно поверхностное копирование - и лучший способ сделать это - сделать LuaState не копируемым и управлять временем жизни lua_State, тогда вы можете передать состояние как shared_ptr .

0
ответ дан 5 December 2019 в 23:14
поделиться

Казалось странным, что boost :: shared_ptr требовал полного типа для создания экземпляра, поэтому я написал этот небольшой тест, демонстрирующий обратное (код в конце).

Я считаю, что проблема не в том, что тип должен быть полным, а во втором аргументе, который вы передаете конструктору shared_ptr , который выглядит как функция-член. Второй аргумент должен быть чем-то вызываемым с одним аргументом-указателем. Если вы хотите использовать функцию-член вашей оболочки, вы можете использовать boost :: bind для адаптации интерфейса.

Может быть, вы имели в виду?:

 LuaState(): L( luaL_newstate(), boost::bind(LuaState::CustomDeleter,this,_1) )
 {
 }

Демонстрация того, что boost :: shared_ptr не требует полных типов:

// forward declarations
struct test;
test * create();
void destroy(test *);

// wrapper equivalent to the one in the question
struct wrapper {
   boost::shared_ptr<test> sp;
   wrapper() : sp( create(), destroy ) {}
};

// actual definitions
struct test {};
test * create() { return new test; }
void destroy(test *t) { delete t; }

// make it executable
int main() {
   test t;
}
1
ответ дан 5 December 2019 в 23:14
поделиться
Другие вопросы по тегам:

Похожие вопросы: