Работя върху вграждането на Lua в C++ проект, който разчита до голяма степен на някакъв наследен C код. Имам няколко въпроса относно събирането на боклука и променливия обхват.
Ето някои фрагменти, свързани с въпросите, които следват:
/* C side */
typedef struct
{
/* fields */
} Element;
typedef struct
{
void * m_elems
unsigned int size;
} Container;
// C API for managing Container and Element
....
int allocContainer(Container*, unsigned int);
void freeContainer(Container*);
Element * getElemByIndex(unsigned int);
// C++ side
struct ElementWrapper
{
private:
Element m_elem;
public:
/* field accessors (NO modifiers) */
};
class ContainerWrapper
{
private:
ContainerWrapper m_cntnr;
public:
ContainerWrapper(int N); // allocates space for N elements
~ContainerWrapper();
// stack alloc'ed variable
ElementWrapper getElementAtIndexStackAllocated(unsigned idx) const;
// heap alloc'ed variable
ElementWrapper * getElementAtIndexHeapAllocated(unsigned idx) const;
};
-- Lua side
wrapper = Container:new(10)
for i =1,10 do
-- get the ith element
el_s = wrapper.getElementAtIndexStackAllocated(i)
el_h = wrapper.getElementAtIndexHeapAllocated(i)
-- do something with retrieved element ..
end
- кога променливите el_s и el_h се събират?
- Трябва ли да използвам ключовата дума „local“ за el_s и/или el_h, за да се уверя, че променливите се отхвърлят в края на всяка итерация в цикъла „for“?
- Индексите започват от 0 в света на C/C++, но 1 от страна на Lua - трябва ли да знам за това в моя код или кодът на tolua++ glue управлява това вместо мен?
Забележка: Умишлено не използвам интелигентни указатели (като boost:shared_ptr), защото C библиотеката обработва цялото разпределение/освобождаване на памет и т.н. и тъй като не знам кога се задейства събирачът на боклук на Lua, всички класове обвивки, които аз изложете на Lua (чрез tolua++), съдържат необработени указатели в стил C като частни членове. Те не се изтриват, когато изложеният C++ клас се събира от Lua GC. По този начин библиотеката C ще изтрие mem, когато и когато е необходимо, сама - и няма опасност от висящи указатели - което може да е случаят, ако използвам споделени указатели или някакъв друг интелигентен указател с преброяване на референции, което може да се обърка от дейностите на Lua GC (надявам се, че схванахте същината - въпреки че знам, че последната част не е много ясна). В крайна сметка, използвам необработени ptrs по добра причина.