Do you actually use dynamic memory?

Member
Posts: 749
Joined: 2003.01
Post: #16
In obj-c do you use some kind of lists that do dynamic memory for you or do you have to free up space yorself and do pointer operations and stuff?

©h€ck øut µy stuƒƒ åt ragdollsoft.com
New game in development Rubber Ninjas - Mac Games Downloads
Quote this message in a reply
Moderator
Posts: 1,560
Joined: 2003.10
Post: #17
You can do either. There's NSMutableArray for dynamically resizable lists, or you can roll your own. Cocoa's memory management system uses a retain/release architecture: Each object has a reference count, which starts at 1 when the object is allocated, is incremented by retain, and is decremented by release. When it drops to 0, the memory is freed. For the parts of your code that don't directly use Cocoa, you can also do things the good old-fashioned C way with malloc/realloc/free and raw pointers.

- Alex Diener
Quote this message in a reply
Member
Posts: 208
Joined: 2005.04
Post: #18
Check out this tutorial on memory management in Cocoa.
Quote this message in a reply
Member
Posts: 749
Joined: 2003.01
Post: #19
Quote:You can do either. There's NSMutableArray for dynamically resizable lists, or you can roll your own. Cocoa's memory management system uses a retain/release architecture: Each object has a reference count, which starts at 1 when the object is allocated, is incremented by retain, and is decremented by release. When it drops to 0, the memory is freed

cool, that's also how blitzmax works.

©h€ck øut µy stuƒƒ åt ragdollsoft.com
New game in development Rubber Ninjas - Mac Games Downloads
Quote this message in a reply
Sage
Posts: 1,066
Joined: 2004.07
Post: #20
It's obvious that I'm just starting CO227 (the advanced C++ class focusing on pointers, OO programming, and the.. uh, advanced stuff Smile) because I have no idea how to work all the dynamic memory things being mentioned. I have some small idea of what malloc does, but beyond that, it looks a whole lot like jibberish to me at the current time.
Quote this message in a reply
Moderator
Posts: 1,140
Joined: 2005.07
Post: #21
Quicky on dynamic memory: (main benefit of having an object on the heap (or dynamic memory) is that it outlives the function you create it in)
C:
The function malloc takes the number of bytes you want to allocate to the heap and returns a pointer to that memory. It returns a void pointer, so you will need to cast that to the particular type you need.
If you want to have an struct myObject (typedefed as myObject) on the heap, you have a myObject pointer (myObject *) and you have to call malloc passing in sizeof(myObject) as the parameter. The call would look like this.
myObject *object = (myObject *)malloc(sizeof(myObject));

If you want to have an array of myObject objects, you just multiply the size. Lets say you want an array of 5 of them:
myObject *objects = (myObject *)malloc(sizeof(myObject)*5);
You can then access each of the five objects as you would a normal array (as in from objects[0] to objects[4])

Objects created on the heap must also be destroyed by you, so when you're done, you must call free(object); (same applies for both)

C++:
Instead of calling malloc and free in C++, you use new and delete (though you can still use malloc and free if you want). Basically, instead of having a pointer then calling malloc with a size, you call new then a type. For example, with the same myObject:
myObject *object = new myObject;

then you call delete with it to destroy it when you're done.
delete myObject;

If your object has a constructor that takes parameters, you just call that constructor with the object.
myObject *object = new myObject(parameters);

With an array, you just add brackets with the number of items.
myObject = new myObject[5];

just remember that you also need a bracket after delete
delete[] myObject;

And there you have it! Dynamic memory. (not as hard as you thought, huh? Rasp)
Quote this message in a reply
Sage
Posts: 1,066
Joined: 2004.07
Post: #22
So if I have a particle system and I want to have a nice dynamic memory set up going for storing the particles (each being two vectors and a float wrapped up into a nice class), how would I code that into my class?

Here's my guess but I just learned this all from reading that and a few past experiences (that almost never went as planned):
Code:
class ParticleSystem
{
...
private:
      Particle *particles;
};

...
ParticleSystem::ParticleSystem(int numParticles)
{
      particles = new Particle[numParticles];
}
ParticleSystem::~ParticleSystem()
{
     delete[] particles;
}
Quote this message in a reply
Moderator
Posts: 1,140
Joined: 2005.07
Post: #23
That would work fine. FYI, with C++ classes, you can just put all your private variables and methods directly under the declaration, since the first unnamed field is automatically private.
Quote this message in a reply
Sage
Posts: 1,066
Joined: 2004.07
Post: #24
I know but I usually have a lot of public functions that I like to list above them. I just forgot to put the public: in the example there. That's part of the ... Smile

One more question. What would I have to do to resize my particle size?
Quote this message in a reply
Moderator
Posts: 1,140
Joined: 2005.07
Post: #25
You would need to create a temporary array with new, copy the elements, then delete the old array and set the pointer of the new array to the private variable.
Quote this message in a reply
Sage
Posts: 1,066
Joined: 2004.07
Post: #26
So something like this?

Attempt 2:
Code:
void ParticleSolver::Resize(int numParticles)
{
    Particle *temp = new Particle[numberOfParticles];
    memcpy(temp, particles, (numberOfParticles * sizeof(Particle)));
    delete[] particles;
    particles = new Particle[numParticles];
    memcpy(particles, temp, (numberOfParticles * sizeof(Particle)));
    delete[] temp;
    numberOfParticles = numParticles;
}

Also, how could I check to see if that function actually works as I want it to (i.e. doesn't just keep eating memory)?

Edit: I'm leaving this here for example purposes but I realized it wouldn't work because I'm making a pointer to a pointer and if I remove the first pointer, the new pointer has no data.
Code:
void ParticleSystem::Resize(int numParticles)
{
     Particle *tempStorage = particles;
     delete[] particles;
     particles = new Particle[numParticles];
     particles = tempStorage;
     delete[] tempStorage;
}
Quote this message in a reply
Oldtimer
Posts: 834
Joined: 2002.09
Post: #27
Actually, the first fields are protected, not private. Smile
Quote this message in a reply
Moderator
Posts: 1,140
Joined: 2005.07
Post: #28
No, that would likely cause a crash. You have to copy it particle by particle. First of all, you will need to have a copy method that will copy all the data from one particle to another. Let's call this copyData. You will also need to store the size of the old array (when you first create it). Let's call it particleSize. You will need to do something like this:

Code:
void ParticleSystem::Resize(int numParticles)
{
     Particle *tempStorage = particles;
     particles = new Particle[numParticles];
     workingSize = (numParticles < particleSize) ? numParticles : particleSize;
     for (int i = 0; i < workingSize; ++i)
          particles[i].copyData(tempStorage[i]);
     delete[] tempStorage;
}
Quote this message in a reply
Moderator
Posts: 1,140
Joined: 2005.07
Post: #29
Fenris Wrote:Actually, the first fields are protected, not private. Smile
I stand corrected. Smile
Quote this message in a reply
Sage
Posts: 1,066
Joined: 2004.07
Post: #30
What exactly would go into the CopyData() function that you have in that code? Remember that I'm just learning all this memory management stuff (and it's hard).

Plus you were right about it crashing Smile. I tried it on my own (just to see) and it didn't work too well. This is my entire .cpp file for the class (if you have time, let me know if anything else is going to go wrong so when I get home from work I can fix it):
Code:
/*
*  ParticleSolver.cpp
*
*  Copyright 2005 SimReality Games. All rights reserved.
*
*/

#include "ParticleSolver.h"

extern int screenWidth, screenHeight;
extern GLint myList;

ParticleSolver::ParticleSolver()
{
    particles = new Particle();
    ptr = particles;
}

ParticleSolver::~ParticleSolver()
{
    delete[] particles;
}

ParticleSolver::ParticleSolver(int numParticles)
{
    particles = new Particle[numParticles];
    numberOfParticles = numParticles;
    ptr = particles;
}

void ParticleSolver::Resize(int numParticles)
{
    Particle *temp = new Particle[numberOfParticles];
    memcpy(temp, particles, (numberOfParticles * sizeof(Particle)));
    delete[] particles;
    particles = new Particle[numParticles];
    memcpy(particles, temp, (numberOfParticles * sizeof(Particle)));
    delete[] temp;
    numberOfParticles = numParticles;
    ptr = particles;
}

void ParticleSolver::MakeNewParticle()
{
    Resize(numberOfParticles + 1);
    ptr += (numberOfParticles - 2) * sizeof(Particle);
    ptr->position.x = screenWidth / 2;
    ptr->velocity.y = -1;
}

void ParticleSolver::UpdateParticles(float frameRate)
{
    int i = 0;
    ptr = particles;
    for(i = 0; i < numberOfParticles; i++)
    {
        ptr->position.x += ptr->velocity.x;
        ptr->position.y += ptr->velocity.y;
        ptr->position.z += ptr->velocity.z;
        if(ptr->position.y < screenHeight)
            ptr->position.y = 0;
        ptr += sizeof(Particle);
    }
}

void ParticleSolver::DrawParticles()
{
    int i = 0;
    ptr = particles;
    for(i = 0; i < numberOfParticles; i++)
    {
        glPushMatrix();
        {
            glScalef(10,10,10);
            glTranslatef(ptr->position.x,
                         ptr->position.y,
                         ptr->position.z);
            glCallList(myList);
        }
        glPopMatrix();
        ptr += sizeof(Particle);
    }
}
Quote this message in a reply
Post Reply 

Possibly Related Threads...
Thread: Author Replies: Views: Last Post
  Troubles With Dynamic Memory Nick 1 2,502 Sep 7, 2005 08:56 PM
Last Post: Nick