LinuxQuestions.org
Review your favorite Linux distribution.
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices

Reply
 
Search this Thread
Old 02-15-2012, 08:34 AM   #1
grob115
Member
 
Registered: Oct 2005
Posts: 528

Rep: Reputation: 32
Creating multiple objects


Hi, am looking for a way to create a number of class objects in a loop. Assuming I have the simple class definition below.
class.h
Code:
#ifndef CCLASS_H
#define	CCLASS_H

class CClass {
public:
    CClass(int i);
    virtual ~CClass();
    int getVar();
private:
    int i;

};

#endif
class.cpp
Code:
#include "CClass/CClass.h"

CClass::CClass(int i) {
    this->i = i;
}

int CClass::getVar() {
    return this->i;
}

CClass::~CClass() {
}
main.cpp
Code:
#include <cstdlib>
#include "CClass/CClass.h"
#include <iostream>
#include <set>

//using namespace std;

/*
 * 
 */
int main(int argc, char** argv) {
    for (int i=0; i<10; i++) {        
	CClass classVariable(i);
	std::cout << i << " - classVariable object created at address: " << &classVariable << " with private variable a = " << classVariable.getVar() << "\n";
    }
    
    std::set<CClass *> classSet;
    int i;

    for (i=0; i<10; i++) {
            CClass * classVariable;
            classVariable = new CClass(i);
            std::cout << i << " - classVariable object created using NEW at address: " << &classVariable << " with private variable a = " << classVariable->getVar() << "\n";
            classSet.insert(classVariable);
    }

    std::set<CClass *>::iterator it;
    i = 0;
    for (it = classSet.begin(); it != classSet.end(); it++) {
            delete *it;
            std::cout << i << " - classVariable object deleted.\n";
            i++;
    }

    return 0;
}
It appears either way the objects, despite getting instantiated with the correct private member variables, are all being stored at the same address. Is there anyway to create 10 different objects all stored at 10 different addresses?
Code:
0 - classVariable object created at address: 0x7fffffffe990 with private variable a = 0
1 - classVariable object created at address: 0x7fffffffe990 with private variable a = 1
2 - classVariable object created at address: 0x7fffffffe990 with private variable a = 2
3 - classVariable object created at address: 0x7fffffffe990 with private variable a = 3
4 - classVariable object created at address: 0x7fffffffe990 with private variable a = 4
5 - classVariable object created at address: 0x7fffffffe990 with private variable a = 5
6 - classVariable object created at address: 0x7fffffffe990 with private variable a = 6
7 - classVariable object created at address: 0x7fffffffe990 with private variable a = 7
8 - classVariable object created at address: 0x7fffffffe990 with private variable a = 8
9 - classVariable object created at address: 0x7fffffffe990 with private variable a = 9
0 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 0
1 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 1
2 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 2
3 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 3
4 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 4
5 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 5
6 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 6
7 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 7
8 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 8
9 - classVariable object created using NEW at address: 0x7fffffffe988 with private variable a = 9
0 - classVariable object deleted.
1 - classVariable object deleted.
2 - classVariable object deleted.
3 - classVariable object deleted.
4 - classVariable object deleted.
5 - classVariable object deleted.
6 - classVariable object deleted.
7 - classVariable object deleted.
8 - classVariable object deleted.
9 - classVariable object deleted.
 
Old 02-15-2012, 09:42 AM   #2
sundialsvcs
Guru
 
Registered: Feb 2004
Location: SE Tennessee, USA
Distribution: Gentoo, LFS
Posts: 5,377

Rep: Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108Reputation: 1108
To make it more obvious what is happening, use three loops. The first one builds the objects. The second one (new...) loops through the collection and prints the variable. The third one destroys the objects.
 
Old 02-15-2012, 09:50 AM   #3
rstewart
Member
 
Registered: Feb 2005
Location: Sunnyvale, CA
Distribution: Ubuntu
Posts: 205

Rep: Reputation: 38
The reason you are getting the same address is that you are actually printing out the address of the variable holding the address of the class object. At least in your second loop, simply remove the & from the "&classVariable" compile and rerun. You will see different addresses.

For the first loop you will probably need to take your class variable and convert it into a void pointer, then you can print out the contents of the pointer (which should then be pointing to your class object).
 
Old 02-15-2012, 10:09 AM   #4
dwhitney67
Senior Member
 
Registered: Jun 2006
Location: Maryland
Distribution: Kubuntu, Fedora, RHEL
Posts: 1,522

Rep: Reputation: 332Reputation: 332Reputation: 332Reputation: 332
Quote:
Originally Posted by grob115 View Post
Hi, am looking for a way to create a number of class objects in a loop.
In the first loop, each object is auto-destroyed at the end of scope of the for-loop block. I do not believe this is what you want. To preserve the existence of the object after you exit the loop, either allocate it on the heap or stuff a copy into a container (e.g. a std::vector) that is declared outside the loop. If you decide to allocate the object, then keep a reference to the address where the object is located. You can use an std::vector, or an std::set as you demonstrated in your code.

A simple example:
Code:
#include <iostream>
#include <vector>

class Foo
{
public:
    Foo(int v) : val(v) {}

    ~Foo() {}

    int getValue() const { return val; }

private:
    int val;
};

int main()
{
    std::vector<Foo*> collection;

    for (int i = 0; i < 10; ++i)
    {
        collection.push_back(new Foo(i));
    }

    for (std::vector<Foo*>::iterator it = collection.begin(); it != collection.end(); ++it)
    {
        Foo* foo = *it;

        std::cout << "Foo object at location " << foo << " contains value " << foo->getValue() << std::endl;

        delete foo;
    }
}
 
Old 02-18-2012, 06:53 AM   #5
grob115
Member
 
Registered: Oct 2005
Posts: 528

Original Poster
Rep: Reputation: 32
Hi, thanks everyone. First, definitely a bug in the second loop. As suggested I have removed the "&" operand and this is printing out the correct addresses as follow in the output. However, as observed in the output also, the first loop is still not working.

Code:
0 - classVariable object created at address: 0x7fffe6577470 with private variable a = 0
0 - classVariable object created using NEW at address: 0x5fe1060 with private variable a = 0
1 - classVariable object created using NEW at address: 0x5fe10b0 with private variable a = 1
2 - classVariable object created using NEW at address: 0x5fe1100 with private variable a = 2
3 - classVariable object created using NEW at address: 0x5fe1150 with private variable a = 3
4 - classVariable object created using NEW at address: 0x5fe11a0 with private variable a = 4
5 - classVariable object created using NEW at address: 0x5fe11f0 with private variable a = 5
6 - classVariable object created using NEW at address: 0x5fe1240 with private variable a = 6
7 - classVariable object created using NEW at address: 0x5fe1290 with private variable a = 7
8 - classVariable object created using NEW at address: 0x5fe12e0 with private variable a = 8
9 - classVariable object created using NEW at address: 0x5fe1330 with private variable a = 9
0 - classVariable object deleted.
1 - classVariable object deleted.
2 - classVariable object deleted.
3 - classVariable object deleted.
4 - classVariable object deleted.
5 - classVariable object deleted.
6 - classVariable object deleted.
7 - classVariable object deleted.
8 - classVariable object deleted.
9 - classVariable object deleted.
dwhitney67, understand perfectly what you are suggesting. However, I'm printing out the addresses within the first loop and within the same iteration. Any idea why this is still using the same address? Also, I've tried doing what you said anyway to put the objects into a std::set. Following is the revised code. However, not sure why I keep on getting an error message during compile time. Any idea what's happening here?
main.cpp:27: error: passing ‘const CClass’ as ‘this’ argument of ‘int CClass::getVar()’ discards qualifiers

Code:
    std::set<CClass> classSet0;
    std::set<CClass>::reverse_iterator classSet0Iterator;
    int i;
    
    for (int i=0; i<10; i++) {        
	CClass classVariable(i);
        classSet0.insert(classVariable);
        classSet0Iterator = classSet0.rbegin();
	std::cout << i << " - classVariable object created at address: " << classSet0Iterator << " with private variable a = " << classSet0Iterator->getVar() << "\n";
    }
 
Old 02-18-2012, 07:00 AM   #6
dwhitney67
Senior Member
 
Registered: Jun 2006
Location: Maryland
Distribution: Kubuntu, Fedora, RHEL
Posts: 1,522

Rep: Reputation: 332Reputation: 332Reputation: 332Reputation: 332
Quote:
Originally Posted by grob115 View Post
Any idea what's happening here?
main.cpp:27: error: passing ‘const CClass’ as ‘this’ argument of ‘int CClass::getVar()’ discards qualifiers
Presumably you have CClass::getVar() declared as:
Code:
int getVar() const;
Thus you will also need to declare your iterator as const as well:
Code:
std::set<CClass>::const_reverse_iterator classSet0Iterator;
 
Old 02-26-2012, 04:03 AM   #7
grob115
Member
 
Registered: Oct 2005
Posts: 528

Original Poster
Rep: Reputation: 32
dwhitney67, that isn't the cause. The class was written as follow so there isn't a const keyword there for the getVar() function.
I tried doing what you suggested anyway by using a const interator and it still throws the same error. Any idea?

CClass.cpp
Code:
#include "CClass/CClass.h"

CClass::CClass(int i) {
    this->i = i;
}

int CClass::getVar() {
    return this->i;
}

CClass::~CClass() {
}
 
Old 02-26-2012, 06:02 AM   #8
dwhitney67
Senior Member
 
Registered: Jun 2006
Location: Maryland
Distribution: Kubuntu, Fedora, RHEL
Posts: 1,522

Rep: Reputation: 332Reputation: 332Reputation: 332Reputation: 332
Quote:
Originally Posted by grob115 View Post
dwhitney67, that isn't the cause. The class was written as follow so there isn't a const keyword there for the getVar() function.
I tried doing what you suggested anyway by using a const interator and it still throws the same error. Any idea?
I was wrong to suggest that a const iterator was necessary; apparently it is not. However, when I attempted to conjure up a simple example, I found that declaring getVar() as const was necessary; otherwise I got the following compilation error:
Code:
g++ Foo.cpp 
Foo.cpp: In function ‘int main()’:
Foo.cpp:35:88: error: no matching function for call to ‘Foo::getVar() const’
Foo.cpp:35:88: note: candidate is:
Foo.cpp:11:9: note: int Foo::getVar() <near match>
Foo.cpp:11:9: note:   no known conversion for implicit ‘this’ parameter from ‘std::reverse_iterator<std::_Rb_tree_const_iterator<Foo> >::pointer {aka const Foo*}’ to ‘Foo*’
To correct the compiler problem, I had to declare getVar() as const. Here's the code:
Code:
#include <set>
#include <iostream>

class Foo
{
public:
    Foo(int v = 0) : var(v) {}

    Foo(const Foo& other) : var(other.var) {}

    int getVar() const { return var; }

    bool operator<(const Foo& other) const
    {
        return var < other.var;
    }

private:
    int var;
};


int main()
{
    std::set<Foo> fooSet;

    for (int i = 0; i < 10; ++i)
    {
        Foo foo(i);

        fooSet.insert(foo);

        std::set<Foo>::reverse_iterator iter = fooSet.rbegin();

        std::cout << i << " - foo object created with variable var = " << iter->getVar()
                  << std::endl;
    }
}
P.S. The address of the (Foo) object that is created in the loop is not very relevant. The object gets destroyed at the end of the loop. The std::set contains a copy of this object.
 
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
How to pass multiple objects into Perl script? AST Programming 1 02-07-2012 07:41 AM
count multiple objects in shell script raggmopp1961 Linux - General 1 07-22-2010 08:56 AM
creating rpm package from filesystem objects arunchandramohanty Linux - General 1 03-19-2010 12:09 PM
LXer: Dynamically creating gui objects on demand in Perl LXer Syndicated Linux News 0 06-12-2009 02:10 PM
Creating Shared objects Anup Kumar Programming 1 09-11-2004 11:45 PM


All times are GMT -5. The time now is 07:02 AM.

Main Menu
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
identi.ca: @linuxquestions
Facebook: linuxquestions Google+: linuxquestions
Open Source Consulting | Domain Registration