Return Struct When Struct has Constructor - page 3

 
R4tna C #:
Could post a code example please of this approach?
I am always curious and happy to learn new things 

Could you be more specific about what you want to see in code? I have mentioned multiple aspects.

 
Dominik Christian Egert #:

Could you be more specific about what you want to see in code? I have mentioned multiple aspects.

Your choice - from the explanation it was not clear to me.

If I see some code examples it would be easier to understand the ideas you are proposing 

 
R4tna C #:

Your choice - from the explanation it was not clear to me.

If I see some code examples it would be easier to understand the ideas you are proposing 


Here a serial number:

struct some_obj
{
        private:
        static ulong s_serial;

        public:
        const ulong serial;

        some_obj() :
            serial (s_serial++)
        {};
};
static ulong some_obj::s_serial = NULL;



Here an example for a UID implementation, although the UID function is just for demonstration purpose and does not provide real UIDs.

struct some_obj
{
        public:
        const ulong obj_uid;

        some_obj() :
            obj_uid (uid_gen())
        {};
};

const ulong uid_gen()
{
    static ulong not_a_real_uid_geenrator = 1;

    
    // Generate some UID
    return(12345 + not_a_real_uid_geenrator++);
}


And a templated filo buffer object, as from my personal code base:


    ///////////////////////////////////////
    //
    //  First In Last Out Buffer
    //

        // Base class object
        template <typename T>
        class _buffer_filo
        {
            protected:

                // Internal state
                int     _size;
                int     _ptr;

                // Buffer
                T       buffer[];
                T       _empty;


            public:

            // Constructor / Destructor

                // Default constructor
                _buffer_filo() :
                    _size(NULL),
                    _ptr(-1)
                { ArrayResize(buffer, NULL); };


            // Buffer functions

                // Reset
                void reset()
                {
                    ArrayFree(buffer);
                    _size = NULL;
                    _ptr = -1;
                };

                // Size
                int size() const
                { return(_ptr + 1); };


            // Pop functions

                // Pop last element
                T pop()
                { return((_ptr < NULL) ? _empty : buffer[_ptr--]); };

                // Pop by decrement
                T operator--(int)
                { return(pop()); };

                // Pop by subtraction
                void operator-=(const int p_in)
                {
                    int cnt = p_in;
                    while( (cnt > NULL)
                        && (_ptr > -1) )
                    { pop(); cnt--; }
                };


            // Assignment operator

                void operator=(const _buffer_filo& p_in)
                {
                    _size = p_in.size();
                    _ptr = ArrayResize(buffer, _size) - 1;
                    for(int cnt = NULL; (cnt < _size) && !_StopFlag; cnt++)
                    { buffer[cnt] = p_in[cnt]; }
                };


            // Access operator

                T operator[](const int idx) const
                {
                    const int _idx = (idx < NULL) ? (_ptr + idx) + 1 : idx;
                    return((_ptr == -1) || (_idx < NULL) ? _empty : buffer[_idx]);
                }
        };


        // Derived simple type class object
        template <typename T>
        class buffer_filo : public _buffer_filo<T>
        {
            public:

            // Constructor / Destructor

                // Default constructor
                buffer_filo() :
                    _buffer_filo()
                { };

                // Destructor
                ~buffer_filo()
                { _buffer_filo<T>::reset(); };


            // Push functions

                // Push new element
                bool push(const T& p_in)
                {
                    _ptr            = (_ptr == _size - 1) ? ArrayResize(buffer, _size + 1) - 1 : (_ptr + 1);
                    _size          += (_ptr == _size);
                    buffer[_ptr]    = p_in;
                    return(_ptr > -1);
                };


            // Assignment operator

                bool operator=(const T& p_in)
                { return(push(p_in)); };
        };


        // Derived complex type class object for pointers
        template <typename T>
        class ptr_buffer_filo : public _buffer_filo<T*>
        {
            private:

            // Local storage

                bool    do_not_destroy;


            public:

            // Constructor / Destructor

                // Default constructor
                ptr_buffer_filo() :
                    _buffer_filo(),
                    do_not_destroy(false)
                { _empty = new T; };

                // Destructor
                ~ptr_buffer_filo()
                {
                    reset();
                    delete(_empty);
                };


            // Buffer functions

                // Do not destroy
                bool dnd(const bool _do_not_destroy = true)
                {
                    do_not_destroy |= _do_not_destroy;
                    return(do_not_destroy);
                };

                // Reset
                void reset()
                {
                    int cnt = _ptr;
                    if(!do_not_destroy)
                    {
                        while(cnt > -1)
                        {
                            if(CheckPointer(buffer[cnt]) == POINTER_DYNAMIC)
                            { delete(buffer[cnt]); }
                            cnt--;
                        }
                    }
                    _buffer_filo<T*>::reset();
                };


            // Push functions

                // Create and push new element
                bool push(const T& _p_in)
                {
                    T* p_in         = new T;
                    *p_in           = _p_in;
                    _ptr            = (_ptr == _size - 1) ? ::ArrayResize(buffer, _size + 1) - 1 : (_ptr + 1);
                    _size          += (_ptr == _size);
                    buffer[_ptr]    = p_in;
                    return(_ptr > -1);
                };

                // Push new element
                bool push(T* p_in)
                {
                    _ptr            = (_ptr == _size - 1) ? ::ArrayResize(buffer, _size + 1) - 1 : (_ptr + 1);
                    _size          += (_ptr == _size);
                    buffer[_ptr]    = p_in;
                    return(_ptr > -1);
                };


            // Pop functions

                // Pop pointer to last element
                T* pop()
                { return((_ptr < NULL) ? _empty : buffer[_ptr--]); };

                // Pop by decrement
                T* operator--(int)
                { return(pop()); };

                // Pop by subtraction
                void operator-=(const int p_in)
                {
                    int cnt = p_in;
                    while( (cnt > NULL)
                        && (_ptr > -1) )
                    { delete(pop()); cnt--; }
                };


            // Assignment operators

                bool operator=(const T& p_in)
                { return(push(p_in)); };

                bool operator=(T* p_in)
                { return(push(p_in)); };


            // Access operator

                T* operator[](const int idx) const
                {
                    const int _idx = (idx < NULL) ? (_ptr + idx) + 1 : idx;
                    return((_ptr == -1) || (_idx < NULL) ? _empty : buffer[_idx]);
                }
        };


Here an object container, and a derived object container showing how you could make an object handle be referencing its belonging to a container


    ///////////////////////////////////////
    //
    //  Unordered container structure
    //

        template <typename T>
        struct object_container
        {
            protected:
            
            // Internal state

                buffer_filo<int>    free_list;

    
            // Object database

                T               _obj_db[];


            public:

            // Constructor            

                object_container()
                { };

    
            // Element functions

                T       set(const int _obj_idx, const T& p_in)          { _obj_db[_obj_idx] = p_in;                     return(_obj_db[_obj_idx]); }
                T       clear(const int _obj_idx)                       { ZeroMemory(_obj_db[_obj_idx]);                return(_obj_db[_obj_idx]); }
                bool    remove(const int _obj_idx)                      { return((_obj_idx > -1) && (free_list.push(_obj_idx))); }

                int     add(const T& p_in)                              { const int tmp = add(); _obj_db[tmp] = p_in;   return(tmp); };
                int     add()
                { 
                    const int arr_size  = ::ArraySize(_obj_db); 
                    return((free_list.size() > NULL) ? free_list.pop() : (ArrayResize(_obj_db, arr_size + 1) - 1)); 
                };


            // Access operator

                T       operator[](const int _obj_idx) const            { return(_obj_db[_obj_idx]); };
                    

            // Get current store size

                int     get_size()  const                               { return(::ArraySize(_obj_db) - free_list.size()); };
                void    free()                                          { ::ArrayFree(_obj_db); free_list.reset(); };


            // Get container association

                bool    associated(const ulong _obj_id) const           { return(true); }
        };





    ///////////////////////////////////////
    //
    //  Unordered container structure
    //  with unique object ID
    //

        template <typename T>
        struct object_container_uid : public object_container<T>
        {
            private:
            
            // Container ID
            
                const uint  container_id;
                T           null_obj;

            
            public:

            // Constructor            

                object_container_uid() :
                    container_id    (__object_container_counter++)
                { };


            // Element functions
                T       set(const int _obj_idx, const T& p_in)          { return(object_container<T>::set(_obj_idx, p_in)); }
                T       clear(const int _obj_idx)                       { return(object_container<T>::clear(_obj_idx)); }
                bool    remove(const int _obj_idx)                      { return(object_container<T>::remove(_obj_idx)); }

                T       set(const ulong _obj_id, const T& p_in)         { if(associated(_obj_id)) { _obj_db[(int)(_obj_id & 0x00000000FFFFFFFF)] = p_in;        return(_obj_db[(int)(_obj_id & 0x00000000FFFFFFFF)]); } return(null_obj); }
                T       clear(const ulong _obj_id)                      { if(associated(_obj_id)) { ZeroMemory(_obj_db[(int)(_obj_id & 0x00000000FFFFFFFF)]);   return(_obj_db[(int)(_obj_id & 0x00000000FFFFFFFF)]); } return(null_obj); }
                bool    remove(const ulong _obj_id)                     { int _obj_idx = (int)(_obj_id & 0x00000000FFFFFFFF);                                   return(associated(_obj_id) && (free_list.push(_obj_idx))); }
                ulong   add(const T& p_in)                              { const ulong tmp = add(); _obj_db[(int)(tmp & 0x00000000FFFFFFFF)] = p_in;             return(tmp); }
                ulong   add()
                { 
                    const int arr_size  = ::ArraySize(_obj_db); 
                    return((ulong)((free_list.size() > NULL) ? free_list.pop() : (ArrayResize(_obj_db, arr_size + 1) - 1)) | ((ulong)container_id << 32)); 
                };


            // Access operator

                T       operator[](const int _obj_idx) const            { return(object_container<T>::operator[](_obj_idx)); }
                T       operator[](const ulong _obj_id) const           { if(associated(_obj_id)) { return(_obj_db[(int)(_obj_id & 0x00000000FFFFFFFF)]); }        return(null_obj); }
                    

            // Get container association

                bool    associated(const ulong _obj_id) const           { return(((int)(_obj_id & 0x00000000FFFFFFFF) > -1) && (_obj_id & 0xFFFFFFFF00000000) == ((ulong)container_id << 32)); }
        };


        // Initialize serial counter
        static uint __object_container_counter = NULL;


Any improvement ideas?

This has been enough code sponsoring for the rest of the year, its your turn now.... 

 
Dominik Christian Egert #:


Here a serial number:



Here an example for a UID implementation, although the UID function is just for demonstration purpose and does not provide real UIDs.


And a templated filo buffer object, as from my personal code base:



Here an object container, and a derived object container showing how you could make an object handle be referencing its belonging to a container



Any improvement ideas?

This has been enough code sponsoring for the rest of the year, its your turn now.... 

Looks interesting - will need a few days to process. Especially as I just got back after a Sat night drinking session lol :)
Reason: