473,513 Members | 2,403 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

Trouble accessing member class' function

3 New Member
Expand|Select|Wrap|Line Numbers
  1. #include <iostream>
  2. #include <vector>
  3.  
  4. class Thing {
  5.     private:
  6.         int value;
  7.         friend class Person;
  8.     public:
  9.         int getValue() { return value; }
  10.         void setValue(const int val) { value=val; }
  11.         Thing (const int val) { value=val; } // Constructor
  12. };
  13.  
  14. class Person {
  15.     private:
  16.         std::vector<Thing> things; // All of Person's Things are stored in a vector
  17.     public:
  18.         void addThing(const int value) { things.push_back(Thing(value)); } // Adds Things to vector
  19.         Thing getThing(const int i) { return things[i]; }
  20.         int getThingValue(const int i) { return things[i].getValue(); } // Get and set value via Thing member function call
  21.         void setThingValue(const int i, const int value) { things[i].setValue(value); }
  22.         int getThingValueFriend(const int i) { return things[i].value; } // Get and set value via friendship from Thing
  23.         void setThingValueFriend(const int i, const int value) { things[i].value = value; }
  24. };
  25.  
  26. int main(int argc, char* argv[]) {
  27.     Person* p = new Person();
  28.     p->addThing(123);
  29.     Thing temp = p->getThing(0);
  30.     std::cout << temp.getValue() << std::endl; // #1: This works
  31.     std::cout << p->getThingValue(0) << std::endl; // #2: As do these two
  32.     std::cout << p->getThingValueFriend(0) << std::endl; // #3: ...
  33.     std::cout << p->things[0].getValue(); // #4: But this doesn't
  34.     delete p;
  35.     return EXIT_SUCCESS;
  36. }
  37.  
I think the code is pretty straightforward; I've removed everything irrelevant, and compressed the whole thing into one chunk. The data structuring won't make much sense now that the program's just a skeleton, but bear with me.

While I realize the "orthodox" way of getting a Person's Thing's value would be #2 or #3, method #4 perplexes me. My compiler (MinGW/gcc 3.4.2) gives this error message:
16 `std::vector<Thing, std::allocator<Thing> > Person::things' is private
33 within this context

I can't figure out how to make expressions like p->things[0].getValue() work, nor why they won't work. I suspect it's because of the expression being evaluated in main's namespace or something, since declaring Person and Thing each other's friends doesn't seem to affect the error at all, but I'm not really sure.

Anyway, while I can (and will) use a better approach to accessing Thing's value, I'd appreciate it if someone could explain to me why method #4 doesn't work, and tell me the simple correction to be made that will leave me banging my head against the desk for not getting it. Thanks.
Aug 2 '07 #1
6 1548
afraze
18 New Member
smoermeli,

Expand|Select|Wrap|Line Numbers
  1. std::vector<Thing> things;
Hi there! i think if you declare this code in class Person's public. Because i compile your code with no error.

p->things[0].getValue(); // also this works..
Aug 2 '07 #2
smoermeli
3 New Member
Argh, of course. All the time I just kept thinking that if I declared the vector public, it would expose the data fields of the objects contained in it - but now that I read your suggestion and thought it over, of course it doesn't expose them. Now I feel stupid.

Thanks. =)
Aug 2 '07 #3
weaknessforcats
9,208 Recognized Expert Moderator Expert
Hi there! i think if you declare this code in class Person's public.
All data is private. Making this public exposes the vector to the world. Now anyone can put junk in the vector. AND if you ever need to change the vector into some other type of container, you will have to change all of the user code that referred to that vector. As a result code like this is called monolithic (one block of stone) because logic and variables are intertwined. Any major resdesign requires a scrap of the original code followed by a rewrite.

The reason #4 won't work is because there is no Person::getValue() method.

So write one:

Expand|Select|Wrap|Line Numbers
  1. int Person::getValue()
  2. {
  3.      return this->Thing::getValue() 
  4. }
  5.  
This is just a simple wrapper.

Making data public to get around an error is not wise. The compiler is trying to tell you that your design is faulty. Public data bypasses the fault.
Aug 2 '07 #4
smoermeli
3 New Member
I'm not sure how that wrapper should work, my compiler says: `Thing' is not a base of `Person'

But anyway, after a good night's sleep I figured out what was the mistake in my thinking. What I initially wanted to do was something like this:
Suppose I want Person to have another type of data, also contained in a vector, for example std::vector<OtherThing> otherthings, where OtherThing could be a subclass of Thing or some other class that has a similar getValue() function. Instead of writing separate functions in Person for every different type and accessing them like this:
Expand|Select|Wrap|Line Numbers
  1. p->getThingValue(index);
  2. p->getOtherThingValue(index);
...and was wondering if I could somehow make them accessible like:
Expand|Select|Wrap|Line Numbers
  1. p->things[index].getValue();
  2. p->otherThings[index].getValue();
What I didn't understand yesterday, but realize now, was that the problem wasn't about Thing or Person accessing things but main accessing it in order to reach Thing's getValue() function; please correct me if I got that wrong. I also understand now why declaring things public is a Bad Idea. Anyway, thanks for your help.
Aug 3 '07 #5
afraze
18 New Member
May be public declaration is not good ..
But it is important that;

1) for what our code will be used?

2) if it is not a big project and just study, we can expose our data to everyone dont be afraid!
Aug 3 '07 #6
weaknessforcats
9,208 Recognized Expert Moderator Expert
my compiler says: `Thing' is not a base of `Person'
Yeah, well so much for compile by eyeball.

This one works:

Expand|Select|Wrap|Line Numbers
  1. int Person::getValue(int arg)
  2. {
  3.      return this->things[arg].getValue();
  4. }
  5.  
but realize now, was that the problem wasn't about Thing or Person accessing things but main accessing it in order to reach Thing's getValue() function; please correct me if I got that wrong.
You have the correct view. The essence of encapsulation is to measure how much code breaks if you change a line of code. Breaking 1000 lines of code rather than 5000 lines of code means better encapsulation. By using private access specifiers, you limit your damage to the member functions.
Aug 3 '07 #7

Sign in to post your reply or Sign up for a free account.

Similar topics

2
1610
by: D. Alvarado | last post by:
Hello, I am running PHP 4. I have this simple class, class CTable { var $m_name; var $m_primary_key_col_name; } then I have a function that takes, as argument, an instance of this class
25
3158
by: John Harrison | last post by:
This code fails to compile on Comeau C++ and VC++ 7.1 (with language extensions disabled) template <class T> struct B { T b; }; template <class T>
2
5761
by: Jeff | last post by:
/* -------------------------------------------------------------------------- Hello, I was experimenting with class templates and specializing member functions and came across a simple problem...
5
2396
by: Sandeep | last post by:
Hi, In the following code, I wonder how a private member of the class is being accessed. The code compiles well in Visual Studio 6.0. class Sample { private: int x; public:
2
2270
by: Steven T. Hatton | last post by:
I find the surprising. If I derive Rectangle from Point, I can access the members of Point inherited by Rectangle _IF_ they are actually members of a Rectangle. If I have a member of type Point...
4
3385
by: keepyourstupidspam | last post by:
Hello, I have a class X with a member function setConfigValues(). I want to access this member function in another class Y. Y is not inherited from X. A member function of class X called run()...
3
4972
by: Olivier BESSON | last post by:
Hello, I have a web service of my own on a server (vb.net). I must declare it with SoapRpcMethod to be used with JAVA. This is a simple exemple method of my vb source : ...
12
3089
by: titan nyquist | last post by:
I have a class with data and methods that use it. Everything is contained perfectly THE PROBLEM: A separate thread has to call a method in the current instantiation of this class. There is...
6
8134
by: Bhawna | last post by:
I am into c++ code maintenance for last 3-4 years but recently I am put into design phase of a new project. Being a small comapany I dont have enough guidance from seniors. Currently I am into a...
0
7386
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
7543
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...
0
7534
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
0
5689
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
0
4749
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and...
0
3236
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The...
0
3226
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
1
805
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.
0
459
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.