Sign in to follow this  
TEUTON

alternate of realloc in C++

Recommended Posts

dave    2187
It's not really bad.

I prefer to have explicit control over the allocation and deallocation of memory in my code. I intentionally never used realloc() in C.

Also it is often the case that at any time you need to resize some memory in C++, you could use one of the containers in either STL or Boost.

Why do you think it is really bad? :)

Dave

Share this post


Link to post
Share on other sites
bodgey    122
Quote:
Original post by blaze02
The realloc func was a horrible function in C. There is no equivalent in C++.


Why is realloc bad? I think it's quite useful if you want to for example implement a vector class in C. I know C++ comes with std::vector but why not use realloc in C?

Bojan

Share this post


Link to post
Share on other sites
MaulingMonkey    1730
Quote:
Original post by TEUTON
Like we have realloc in C what can we do to reallcate the memory in C++.

I don't think there is any keyword.


Nope. Instead, use std::vector.

int * foo = malloc( sizeof(int) * 30 );
foo = realloc( foo , sizeof(int) * 40 );
assert( foo );
//will crash/screwup on allocation failure (I was too lazy to add error handling
free( foo ); //if we return an error, we'll need to free() there too, remember!


Becomes:

std::vector< int > foo( 30 );
foo.resize( 40 );
//will throw std::bad_alloc on allocation failure
//cleans up after itself using a destructor

Share this post


Link to post
Share on other sites
Skarsha    132
If I remember rightly, if vector ever needs to change the size of the memory allocated to it (either up or down), it _always_ copies the lot, wheras realloc would sometimes be able to change the size of the block but keep the address the same, thus not requiring moving data. This would probably happen whenever the new size passed to realloc was smaller than the previous size (depends on implementation)

vector makes this slightly nicer by overallocating space for itself so that if it gets slightly larger it doesn't need to change the size of the memory chunk. I also think you can tune the overallocation on a per vector-type basis, but I haven't tried yet.


Dave:
However, I don't see how realloc is not explicit control - is it because it decides whether or not to change the pointer.


I personally think allocation in C++ is way more obfuscated, restrictive and inconsistent than in C. However, it is faster (although it may just be that's only because they decided not to let you do the slow stuff - like resizeable chunks).


You can of course do this:

void* myRealloc(void* ptr, size_t new, size_t old) { // <--- NOTE THE "old" size.
void* new_ptr = ::operator new(size_t);
memcpy(new_ptr, old_ptr, (old > new) ? new : old);
::operator delete(ptr);
return new_ptr;
}
// Not sure if that's the right syntax, but I hope you get the idea.


You almost always know how big the allocation is when you want to resize, so requiring the "old" value shouldn't be too much of a hassle.

Of course, this is not as fast as realloc(), since it always moves the data.

Share this post


Link to post
Share on other sites
MaulingMonkey    1730
Quote:
Original post by darkchrono4
Doesn't malloc actually allocate more space then desired so that if you need to change the space with realloc it probably won't have to move the data?


That's a possibility. Of course, if you don't use realloc(), that could mean a lot of space allocated for no good reason that will go to waste, unless you keep the extra relatively small, in which case you probably will have to move the data sometime.

It's equivilant, std::vector, usually only gives you extra data if you end up growing it past it's initial size:

resize( n ) {
if ( n > capacity() ) grow_memory_to( std::max( n , 2 * capacity() ) );
...
}


By choosing whichever is larger of N and 2*capacity() (or 1.5* on some implementations), this allows inserting elements at the end to become amortized constant time, meaning performance won't sink into the drain with large data sets push_back()ing elements if you didn't reserve() enough memory (you guessed incorrectly), and if you did reserve() the right amount of memory (you were right) you won't be wasting memory.

Quote:
I personally think allocation in C++ is way more obfuscated, restrictive and inconsistent than in C. However, it is faster (although it may just be that's only because they decided not to let you do the slow stuff - like resizeable chunks).


Not sure why you'd say obfuscated.

While new/delete might be fairly restricted, when you look at the STL containers (part of the standard C++ library), each one takes a plug-and-play allocator, meaning each container isn't hardwired to a single allocation method. I'd say that's less restrictive.

Not sure what you're refering to when you say inconsistent (although there are quite a few inconsistencies in C++ in general). And none of this "they decided not to let you do the slow stuff" junk:

For objects, std::vector offers the C realloc equivilant with appropriate object (de)constructing.
You can still use realloc with malloc/free for raw memory (#include <cstdlib>)

Share this post


Link to post
Share on other sites
jpetrie    13132
Quote:

Doesn't malloc actually allocate more space then desired so that if you need to change the space with realloc it probably won't have to move the data?


It allocates more space that requested because it has to store some bookkeeping information. Concievably it could allocate more "actual memory" than you requested on the off chance that you'll want to call realloc, but I doubt any implementation actually does that because it won't be very useful (and will, in fact, be wasteful) the majority of the time.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this