auto_ptr and their usability with STL containers

Aaaahh... Smart pointers..aren't they one of the best things that has happened to C++. They are also sometimes called Managed pointers. I am not going to talk about them right from introduction, so if you are unaware what they are and what are their uses, then try figuring them out through the web-searches or @ codeguru... my fav place as far as C++ is concerned.

Ok..Ok..not ready to search for them...fine.. I will try giving a very brief description. Remember when you use pointers in C++ with dynamic memory management, it's such a headache to get them going and finish them off once you are done? If you did a new or new[], you need to have a corresponding delete or delete[], so that the allocated memory is freed up and the destructor for the new-ed object is called. Also, when you are done with the delete/delete[], freed-up the memory, you need to cautiously set the pointer to NULL, so that you won't try dereferencing it after the de-allocation assuming it points to a valid object. (Recall Dangling pointers. They could be disastrous if dereferenced!)

But just imagine that you could use pointers in the same way you used to do and forget about the headache of the deleting (and optionally NULLing it)? How would that be? Wouldn't that be cool and care-free? ...and that is what is made possible by these managed pointers/smart pointers. They are really smart and they exist in wide varieties.

For now, I would limit my post to just one of that category which is the standard auto_ptr (read auto-pointers). They are a part of C++. They own the dynamically allocated object and then perform the automatic cleanup whenever the object goes out of scope or is not needed. Now, if at some stage you want the manual ownership back they have this function member - release(), make a call to it and all the headache is back yours.

[CODE]
//Example showing a bad situation with naked pointers
void MyFunction()
{
        MyClass* ptr( new MyClass);
        /*.some more code.*/
        delete ptr;
        ptr=NULL;
}

In this scenario, just in case of some exception it's possible that somehow the delete ptr; did not happen...Disasterous..a memory leak! There's more - suppose, in the destructor of MyClass, you call for some resource release like close database connections, releasing file handles or release semaphores, locks etc. All resources are blocked and there's no way out. There could be many more aweful situations.

Now, lets use an auto_ptr and see how it makes life easy:

[CODE]
//Situation above tackled using auto_ptr
void MyFunction()
{
        auto_ptr<MyClass> ptr(new MyClass);
        /*.some more code.*/
}

There is no need to explicitly call a delete; as soon as ptr goes out of scope the destructor of MyClass is called and the object is freed. You should note that auto_ptr only handles allocations with new and not those done with new[] or malloc or any other memory allocation routine for that matter. For those, refer to the following posts - Handling dynamic array allocations, Custom deleters with smart pointers, Free New, Delete Malloc

You can even transfer the ownership of an auto_ptr to another auto_ptr, to another function or free/reset it to use it again.

Here's an example showing the transfer of ownership from one auto_ptr to another.

[CODE]
        //Example showing transfer of ownership.
        auto_ptr<MyClass> autoptr1(new MyClass);
        auto_ptr<MyClass> autoptr2;
        autoptr2 = autoptr1;
        //Now autoptr2 owns the pointer & autoptr1 doesn't
        autoptr1->MyFunction(); // ERROR !!!
        //autoptr1, now is a null pointer

However, one very interesting and important fact about auto_ptr's is that their copies are not equivalent as is the case with naked pointers.
  • Consider STL containers or some generic algorithms/functions like sort. There is no restriction by the standard on the vendors of the STL implementers that the containers won't make a copy of the members being added into it (and probably do nothing with it!). In fact, for example, the implementations of the vector class make a copy of the original object and store inside them. We know auto_ptr copies are not equivalent due to the strict ownership semantics. You might be safe in just having those auto_ptrs stored inside a vector but you get a few examples around this in the Gotw link below that show how the problem comes out in the open, for example, with say, a sort algorithm that holds a copy of an element as a pivot? There is nothing to guarantee or prevent that.

  • Another disastrous situation would be when you are initializing (setting/assigning) another auto_ptr object with an object held by the vector. You would think that the object inside the vector is okay and retains the same state but it will not. The ownership by this time would get transferred to the external object just initialized/assigned.

  • What if there is a member function that returns the contained vectors element is returned by value?

  • What if you make another copy of the vector? Or for that matter, create some other container out of its elements?

  • Use of member functions of vector like - constructor, assign, insert, resize - will they succeed? Will they definitely succeed?

It just gets too messy to handle. Sure some operations will work out fine but quite a few will not and you would need to keep worrying about 'em.

To help us out of this disaster, the C++ standards did some tweaking. The copy constructor and the copy assignment operator of auto_ptr take a reference to a non-const right hand side objects and the standard containers' insert() takes a reference to a const and hence auto_ptr cannot be used. It will just not allow you to create a copy of auto_ptr inside the vector (standard containers) members. That will cause you compilation errors on a compliant compiler. Nice solution..isnt it? But still, as a strict guideline..we should not use the auto_ptr wherever a copy of theirs is expected to be made.

For more information, visit these : Using auto_ptr effectively by Herb Sutter, Smart Pointers - What, Why and Which, Smart pointers

Cya!

Firefox Browser


The Firefox browser is an excellent browser among the availables today. I found an interesting article that compares the Firefox browser and the IE browser (Internet Explorer).

So of the interesting features are;
- Tabbed browsing
- Popup blocking
- Prevent scripts from doing various things
- More control over text zooming
- Block images from third party sites
- Cross-platform
- Open Source
- Huge range of extensions and ease of installing extensions

Read all the 101 things that the Mozilla browser can do that IE cannot.

I installed some more extensions for Firefox today which are listed below.

- CustomizedGoogle
Adds a selected set of search sites like yahoo, ask jeeva,.. to your google search result page. Also provide an easy customization.
- Tab X
This is an extension I was looking for. This adds a close button to each browser tab which is not availble in default Firefox.
- Gmail Notifier
Browser notifies for new mails. Still only the new mail arrival is shown, but showing the mail headings would improve the extensions popularity.
- Resize Search Box
Another feature that I was expecting from the default Firefox installation, how ever now I can resize the search box at the top right corner.
- Show IP
This shows the IP of the site.
- Flash Block
Allows the user to decide whether to play or stop the flash contents in the site.

What is your idea on these extensions?

Microsoft sued Google

As the search engine competition is in a top level with google, yahoo and microsoft competing, I heard a news today as follows.

Microsoft sued Google yesterday (07.19.2005), for hiring one of their top employer to head a new research lab in China. As Microsoft argued that taking such a position in a direct competitor is illegal. And also Microsoft point the finger towards Google for encouraging him to do so.

As news expalined, Dr. Lee is a well known character in the industry and he has worked for Silicon Graphics and Apple.

When google is growing so fast while offering new wide range of services, losing Dr. Lee will be a huge issue for Microsoft to retain in the competition.

So we'll look forward to see the continuation.

One interesting point I noticed was the demand that Bill Gates have given to the qualified professional in this industry, as he says that the major problem is talented computer science graduates.

Read More...
www.forbes.com
www.pcpro.co.uk

Koenig look-up and namespaces

I was running through some of the posts on codeguru and then suddenly saw this name referenced in Andreas Masur's post - "Koenig Lookup". I had heard it for the first time since I started with C++ and to be specific namespaces. So, I though of starting a look-up for myself and find what it really was! This post would be an introduction to the concept which we frequently use knowingly and most of the times unknowingly. Here it goes:

Keonig look-up is an algorithm devised by Andrew Koenig. This algorithm is also sometimes known as Argument-dependent Lookup. These days, it is used in all the standard conforming compilers in C++ which handle cases as shown in the example code below:

[CODE]
namespace MyNamespace{
class A {};
void func(A);
}

MyNamespace::A a; // global object of MyNamespace::A class.

//main method.
int main(){
func(a); // OK - MyNamespace::func is called.
}

Neither a using-declaration nor a using-directive appears in code above. And yet, the compiler will do the needful and that is correctly identifying the unqualified name "func" as the function declared in namespace MyNamespace by applying the algorithm we are talking about. How does it work? The algorithm tells the compiler to look at not just the usual places such as local scope, but also the namespaces that contain the argument's type. Thus, in the following line of code, the compiler finds that the object a, which is the argument of the function func, belongs to the namespace MyNamespace. So, it looks at that namespace to locate the declaration of "func", "guessing" what we wish to do.

Without this, namespaces would be imposing an unacceptable burden on the programmer, who would have to repeatedly specify the fully qualified names, or instead, use numerous using-declarations. There is abundant debate on the topic of advantages and disadvantages of this algorithm but lets see this example to support this feature.

[CODE]
#include
using std::cout; //using declaration
int main(){
cout<<"hello world!"; //OK, operator <<>
}

The using declaration puts std::cout into the scope of main(), thereby enabling us to use the non-qualified name "cout". However, the overloaded <<>

[CODE]
std::operator<<(cout, "hello world!");

Isn't it a pain-saving appreciable feature. It's interesting to find out about things that we usually do unknowingly. It add value to our knowledge. Cheers.

Casting cv-qualifier and function pointers to void*

Okay..so this is my first post to this blog of mine. This post is a result of a very fine discussion that I had with some of the Gurus at http://www.codeguru.com. I thought I would compile the stuff from that and present it here.

Before I proceed any further I would like to thank the members of Codeguru who participated with keen interest and helped me get the concept right. Thanks to - Graham, SuperKoko, Smasher/Devourer, Wildfrog, NoHero and Improving.

The question was - Can void pointers point to const, volatile and function pointers? Explain.

The answer is - Quotes from MSDN:
"If a pointer's type is void *, the pointer can point to any variable that is not declared with the const or volatile keyword."
AND
"A void pointer can point to a function, but not to a class member in C++."

Thats pretty much it but lets go through the explanation to get to the basic reasons why MSDN negates the possibilities.

const and volatile are collective named as cv-qualifiers by the standard and a basic principle is that we are not allowed to lessen the amount of cv-qualification of an object. If we were to assign a cv-qualified object to a void pointer, then we could cast them back to a non-cv-qualified pointer to the original object. This steals away the whole essence of the cv-qualification of the objects while the intention of the standard is that only const_cast can remove cv-qualification from an object.

The standard treats const and volatile identically as far as their syntax and restrictions are concerned. The standard intentionally makes it hard for us to lose the cv-qualification of an object, since this is almost always an error in coding, not that its impossible.

You could use this as an example:
[CODE]
volatile int arg = 0;
void * ptr1 = &arg; // Valid but it won't be volatile anymore

A better way to do this could be:
[CODE]
volatile int arg = 0;
volatile void * ptr1 = &arg;

Okay, so that's for the CV-qualifiers. Now lets get back on track with the case of function (class-member functions as well as non-member functions) pointers.

Let's take an example:
[Code]
#include<iostream>
using namespace std;

//This creates a typedef called IntFuncPtr which is a pointer to a function
// that takes no arguments and returns an int.
typedef int (*IntFuncPtr)();

// An example class with a single member function.
class A {
public: int f() { return 1; }
};

//Note this function has the proper signature to be addressed by an IntFuncPtr.
int g() { return 2; }

int main() {
void *pVoid;

pVoid = g; //OK: cast from int (*)() to void*
cout << ((IntFuncPtr) pVoid) () << endl;
pVoid = A::f; //ERROR: can't cast from int (A::*)() to void*
return 0;
}

In this program, Visual C++ 6.0 will allow to make an implicit conversion from a (non-class member) function pointer to a void pointer, in the line pVoid = g. In the following line, we cast that pointer back to its appropriate type and use it to call the function it points to, to demonstrate that it holds the correct value. The line after that, attempting to assign a class member function pointer to a void pointer, does not work.

So, we see that we can use void* to point to non-member functions but not member functions. Is this really true?? Even if we are able to get the non-member functions part going, is it portable??? Comeau compiler is considered to follow the C++ standards to the closest and running this code there did not allow what VC++ allowed easily. It gave the following error message - "A value of type int (*)() cannot be assigned to an entity of type void*."

The reason for this is well explained by Herb Sutter in his More Exceptional C++. He says : "Although a void* is guaranteed to be big enough to hold the value of any object pointer, it is not guaranteed to be suitable to hold a function pointer; for example, on some platforms a function pointer is larger than an object pointer." That is, in general, for a member function pointer or a non-member function pointer.

Here's an example that illustrates this for the case of member function pointers:

[CODE]
#include<iostream>
using namespace std;

class A
{
public:virtual void f();
};

class B
{
public:int x;
};

class C : public B, public A
{
};

int f()
{
return 0;
}

int main()
{
void *p=reinterpret_cast<void *>(f);
cout << sizeof(&A::f) << " "<< sizeof(static_cast<void (C::*)()>(&A::f)) << endl;
return 0;
}

Outputs:
8 8 (With GCC)
12 12 (With BC++)
4 8 (With VC++)

While sizeof(void*) will gives you 4, with above.

You might get better affirmative results for classes with simple inheritance but with multiple inheritance (the case in the program), virtual inheritance, virtual functions and in some more complex scenarios, you could get the size of the function pointers greater than sizeof(void*), may be 4, 8 and sometimes 12 or even greater. They are very compiler dependent and class dependent.

You can't even assign a pointer to non-member functions to a void* for the same reasons (even if some compiler would allow you doing so), they are not guarenteed to be of the same size. These are however relatively portable than the case of member-function pointers and that is why MSDN says you can (for non-member functions) atleast on MS platform. But, you know that's not portable. A work-around could be using reinterpret_cast to cast a function pointer to another function pointer type (say, any one that you can use throughout your code base for consistency) and then cast it back to it's original type. The standard guarantees that to work. But the drawback is that you lose type-safety, which itself is not a very good thing to do in ideal scenarios.

Further reading and references: online Comeau compiler at Comeau online , Recursive Declaration.

Cheers!!!

TechNewsWorld


Today I found a good web site which consists of news on new Techs. That is www.technewsworld.com. Seems it provides news in all most all the techincal fields. I was mainly focused on the Open Source portion.

Some of the interesting news I found today are;

  • Firefox Patch
    Patch releasing has two practices. One is to release patches at the end of each month and the other is to realese as soon as it is ready.
    I feel that patch releasing as soons as possible is the best way since recovery of an attack will be much harder than applying a patch even in a large scale organization.

  • One-in-Ten-Web-Users-Have-a-Taste-for-Spam
    As the news explains 39 percent of the people still reading the messages and clicking on links embedded in the emails. As they says, this is a known method for spammers to detect if an email address is being used, and as a result 57 of the latter group reported that they started receiving more spam.

  • Sun-Open-Sources-Its-Authentication-Technology
    Sun Microsystems moves towards Open source. But I wish the complete java platform not to become Open-Source.
  • Google News

    "Google News" provides a well organized and a customizable view for NEWS.

    You can customize the viewed news by providing key words. And also the news can be prioritize according to your requirements. So news searching and organizing is done by Google, we just have to watch it.



    http://news.google.com/


    I have created a customized News View for me. You can check my configurations and even you can use that as your customized view.

    My Customized News View

    Learning C++

    This blog would be a collection of some quality issues related to the C++ Programming Language. A compilation of my activities on Codeguru. Hope this comes out to be of help to you people and of course me.

    Cheers to my 2nd blog.
    [ http://abnegator.blogspot.com ]

    JASIC?

    Someone recently mentioned a new up and coming BASIC language product called KBASIC and asked me what I thought. I went to Google and found the site. What I discovered there was so complicated that it reminded me of programming in Java using the Eclipse IDE. Eclipse is an excellent IDE, at least in the sense that it makes programming in Java practical (possible?). You need all the power of Eclipse because Java is a big, heavy and complicated way to write software.

    KBASIC seems to emulate Java. Even the style of object orientation presented is very Java-like or C#-like and some syntax is borrowed directly from Java. Why do this? BASIC shouldn't need an industrial strength IDE that is as complicated as the cockpit of an F-15.

    This is the sort of thing I am trying to avoid with the new BASIC programming language I'm working on. Java is a mountain of rules and exceptions that the programmer must navigate, never forgetting to dot i's and cross t's. Why make a BASIC that emulates Java? This is the sort of thing that caused outcry when Microsoft did away with Visual Basic and replaced it with VB.Net.

    I know that some people enjoy mastering complexity, perhaps as a way to find satisfaction in their work. This is incompatible with the way BASIC programming should be. BASIC should be small, simple and fun.

    On Modernizing BASIC

    dave b. responded to my previous post with this (amongst other things):
    I hope this nostalgia over the old BASIC command set and the "small is beautiful” fallacy won't hold LB back from evolving into something really useful (which is what programming languages should be).


    Really useful for what, Dave? Go and ask the Liberty BASIC community if Liberty BASIC is useful and they will answer with a resounding yes. It is useful for getting a quick program together, useful for learning to program, useful for having fun with a computer, and more too. To make a comparison, Java is also a useful programming language, but it isn't necessarily useful for the same things. There is no universally useful programming language.

    I agree with a lot of your ideas, and if you read all of my posts, I think you'll agree that I don't have the simplistic mindset that you seem to imply that I have. I understand abstraction in software better than you apparently think I do.

    Nostalgia has nothing to do with Liberty BASIC's faithfulness to classic BASIC syntax, at least not on my part. This is a matter of marketing. You welcome the C-style of doing things with functions. A lot of other people do not. They want an old-style BASIC. I am marketing to these other people. Your advocacy of mutating BASIC syntax into something that is more "modern" does create a new language that is not BASIC, IMHO. Eliminating old BASIC commands and replacing them with functions turns a lot of people off.

    I am working on a new BASIC in part to break the backwards compatibility chain with Liberty BASIC. That doesn't mean of course that my new language will necessarily take the direction that you advocate. OPEN "filename.ext" for INPUT as #1 will still be there. I agree with your point that the syntax for controlling widgets in Liberty BASIC is bad, and it will be replaced in the new BASIC. I will do things differently and in an unexpected way, and not to be deliberately contrary but for a reason. I intend to lead with this new language, not follow.

    BTW, a lot of people like Liberty BASIC the way it is and don't seem to need anything else. You have decided to move on to another tool that meets your needs better and that's great.

    Don't expect Liberty BASIC to become anything but what it is. This is beginning to feel like you're beating a dead horse. :-/

    Check out this stream