473,404 Members | 2,195 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,404 software developers and data experts.

Advanced Functions

I just bought a book and he gave me an example similar to this one and forgot to explain it. Please see my notes and questions in the code and if I'm understanding anything wrong please explain. My Q's are in caps to differentiate the comments. Thanks.

Expand|Select|Wrap|Line Numbers
  1. #include <iostream>
  2.  
  3. using namespace std;
  4.  
  5. class Square
  6. {
  7.       public:
  8.              Square();
  9.              Square(int side);
  10.              int GetSide() {return *itsSide;}
  11.              Square & operator= (Square & rhs); 
  12.              const Square & operator++ (); //WHY IS THIS CONST?
  13.              const Square operator++ (int); //WHY IS THIS CONST?
  14.  
  15.       private:
  16.             int * itsSide; //pointer to int
  17. };
  18. //default constructor
  19. Square::Square()
  20. {
  21. itsSide = new int(10); //Assigns new memory on heap for the calling 
  22.                        //object and assigns 10
  23. }
  24. //overloaded constructor
  25. Square::Square(int side) 
  26. {
  27. itsSide = new int(side);//Assigns new memory on heap for the calling 
  28.                        //object and assigns the passed in parameter
  29. }
  30. //overloaded assignment operator    
  31. Square & Square::operator= (Square & rhs)
  32. {
  33.  
  34.        delete itsSide; //WHY IS IT DELETING THE CURRENT MEMORY ADDRESS
  35.                        //THAT THE POINTER POINTS TO?
  36.        itsSide = new int; //Assigning new address to pointer
  37.        *itsSide = rhs.GetSide(); //get the value for the crate object 
  38.                                  //and assign to the new address 
  39.        return *this; //WHAT IS BEING RETURNED HERE?
  40. }
  41.  
  42. const Square & Square::operator++ ()
  43. {
  44.       ++(itsSide); //WHY IS THIS BEING INCREMENTED WITHOUT BEING DEREFERENCED?
  45.       return *this; //WHERE DOES THIS VALUE GET RETURNED TO?
  46. }
  47.  
  48.  const Square Square::operator++ (int)
  49. {
  50.       Square temp(*this); //dereference address being passed in 
  51.                           //and assign value to temp
  52.       ++(itsSide); //WHY IS THIS BEING INCREMENTED WITHOUT BEING DEREFERENCED?
  53.       return temp; //WHERE DOES THIS VALUE GET RETURNED TO?
  54. }       
  55.  
  56. int main()
  57. {
  58.     Square box; //default constructor called
  59.     Square crate(100); //overloaded constructor called
  60.     cout << box.GetSide() << endl; //output
  61.     cout << crate.GetSide() << endl; //output
  62.  
  63.     box = crate; //overloaded assignment operator called
  64.     cout << box.GetSide() << endl; //output
  65.  
  66.  
  67.    crate++; //Overloaded postfix operator
  68.    cout << crate.GetSide()<< endl; //WHY IS THIS RETURNING 4064624?
  69.  
  70.  
  71.  
  72.     system("pause");
  73.     return 0;
  74. }
  75.  
Jul 24 '10 #1

✓ answered by Banfa

You do know that USING CAPITALS ON THE INTERNET IS CONSIDERED TO BE SHOUTING AND RATHER RUDE do you?

No the modification you made to postfix increment does not work because it does not implement the correct semantics.

The semantics of postfix increment are increment the value of the object and return its original value. Your version does not do this it increments the value of the object and returns the new value which is the semantics for prefix increment.

That is why the author uses a temporary object, its the only way to do it and because a temporary object is used the function needs to return by value not by reference hence the original implementation.

The only change I would consider is implementing postfix increment in terms of prefix increment, in a complex class this has the effect of reducing the number of times that the incrementing logic needs to be implemented.

Expand|Select|Wrap|Line Numbers
  1. const Square Square::operator++(int)
  2. {
  3.       Square temp(*this); //dereference address being passed in 
  4.                           //and assign value to temp
  5.       ++(*this);
  6.       return temp;
  7.  
The above logic works for any class if it has implemented prefix increment.

6 4354
Banfa
9,065 Expert Mod 8TB
WHY IS THIS CONST?

Imagine using ints for a moment the operators at line 12 and 13 are pre and post increment, do you think either of these lines makes sense?

Expand|Select|Wrap|Line Numbers
  1. int a = 10;
  2.  
  3. ++a = 7;
  4. a++ = 6;
  5.  
Line 4 doesn't compile, line 3 although it compiles is undefined behaviour and should be avoided. Assigning to the return value of the post or pre increment operator does not make semantic sense, the return values are effectively constants and there for the post and pre increment operators for your Square class return const. To maintain the semantic meaning of the operator.

Expand|Select|Wrap|Line Numbers
  1.        delete itsSide; //WHY IS IT DELETING THE CURRENT MEMORY ADDRESS
  2.                        //THAT THE POINTER POINTS TO?
  3.        itsSide = new int; //Assigning new address to pointer
  4.        *itsSide = rhs.GetSide(); //get the value for the crate object 
  5.                                  //and assign to the new address 
  6.  
Well if you have a buffer allocated using malloc inside a class normally when you copy using the assignment operator, operator=, you have to get rid of the old buffer allocate a new buffer and copy the contents of the object being copied from to the current object.

This code maintains that strict structure. However in this particular case it is not strictly required to free and re-allocated the memory. In fact in my opinion allocating memory for a single int like this is just introducing unrequired complexity to the code. Since an int normally takes either the same number of bytes or fewer bytes to store than a pointer just having a int directly in the class either uses no extra memory or saves memory and reduces code complexity by not having all the memory allocations and releases.

Expand|Select|Wrap|Line Numbers
  1.        return *this; //WHAT IS BEING RETURNED HERE?
  2.  
The current object by value.

Expand|Select|Wrap|Line Numbers
  1.       ++(itsSide); //WHY IS THIS BEING INCREMENTED WITHOUT BEING DEREFERENCED?
  2.  
Almost certainly an error in the code causing undefined behaviour.

Expand|Select|Wrap|Line Numbers
  1.       return *this; //WHERE DOES THIS VALUE GET RETURNED TO?
  2.  
The code that invoked the operator.

Expand|Select|Wrap|Line Numbers
  1.     crate++; //Overloaded postfix operator
  2.     cout << crate.GetSide()<< endl; //WHY IS THIS RETURNING 4064624?
  3.  
Because of the coding error in operator++
Jul 24 '10 #2
Thanks for helping Banfa. I understand almost all your explanations. However i don't know how to fix the problem. I hate asking for answers. So maybe you can give me a hint as to what is wrong in the operator++ function?
Jul 25 '10 #3
Banfa
9,065 Expert Mod 8TB
Well in the class I would change
int * itsSide; //pointer to int
to
int itsSide; //int
and then resolve all the places treating it as a pointer but if you don't want to do that then on the lines like this

Expand|Select|Wrap|Line Numbers
  1.       ++(itsSide); //WHY IS THIS BEING INCREMENTED WITHOUT BEING DEREFERENCED?
you have correctly observed that there is an issue with dereferencing itsSide (or in fact not dereferencing it) you just need to fix it.
Jul 25 '10 #4
I fixed the overloaded prefix operator but the post fix does not work. It outputs 0... And a new question arised: //Why not make the postfix function return a reference like the prefix function? This way, we could just return '*this'. I tried and it works. Is this ok to do? If so then why did the author go thru the hassle of creating a temp object and returning by value?

Expand|Select|Wrap|Line Numbers
  1. const Square & Square::operator++ ()
  2. {
  3.       ++(*itsSide);
  4.       return *this; 
  5. }
  6.  
  7.  
  8.  const Square & Square::operator++ (int)
  9. {
  10.       ++(*itsSide);
  11.       return *this; 
  12. }
  13.  
  14.  
Jul 26 '10 #5
Banfa
9,065 Expert Mod 8TB
You do know that USING CAPITALS ON THE INTERNET IS CONSIDERED TO BE SHOUTING AND RATHER RUDE do you?

No the modification you made to postfix increment does not work because it does not implement the correct semantics.

The semantics of postfix increment are increment the value of the object and return its original value. Your version does not do this it increments the value of the object and returns the new value which is the semantics for prefix increment.

That is why the author uses a temporary object, its the only way to do it and because a temporary object is used the function needs to return by value not by reference hence the original implementation.

The only change I would consider is implementing postfix increment in terms of prefix increment, in a complex class this has the effect of reducing the number of times that the incrementing logic needs to be implemented.

Expand|Select|Wrap|Line Numbers
  1. const Square Square::operator++(int)
  2. {
  3.       Square temp(*this); //dereference address being passed in 
  4.                           //and assign value to temp
  5.       ++(*this);
  6.       return temp;
  7.  
The above logic works for any class if it has implemented prefix increment.
Jul 27 '10 #6
Thanks for the detailed response. I didn't mean to shout. I was just trying to make the question stand out. I have made the proper changes.
Jul 27 '10 #7

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

Similar topics

5
by: hokiegal99 | last post by:
A few questions about the following code. How would I "wrap" this in a function, and do I need to? Also, how can I make the code smart enough to realize that when a file has 2 or more bad...
99
by: David MacQuigg | last post by:
I'm not getting any feedback on the most important benefit in my proposed "Ideas for Python 3" thread - the unification of methods and functions. Perhaps it was buried among too many other less...
1
by: Houston | last post by:
I have been able to get several basic databases to function both in playing around and functional ones on the web but they have all been pretty simple. I am now trying to develop a database for the...
7
by: BlueDragon | last post by:
The place where I work is moving to MS SQL Server from Lotus Notes. I have done a lot of coding in Lotus Notes, and have, I suppose, intermediate skills in basic SQL -- queries, insert, updates,...
4
by: st_ev_fe | last post by:
Hi people, I've been doing C for about 7 years now. But I'm new to C++. I've decided that C++'s operator overloading could be very handy. I'm writing something much like auto_ptr, except for...
0
by: kt | last post by:
We want to automatically turn off the error reporting options using Windows API functions for the following functions area Click on Start, Settings, Control Panel, System, the Advanced tab and...
4
by: Gaijinco | last post by:
I read somewhere that printf and scanf had "advanced features" and they point to: scanf("%",line); // line is a string as an example, where scanf() acts like gets() I try to look of more of...
0
by: Sharath | last post by:
Quality Globe is Glad to Offer you the Fast Track course on Automation, QTP Basics and Advanced, and Quality Center Starting Date: June 4th, 2007 Timings: 10 AM to 3:30 PM Duration: 50 Hours ...
20
by: J de Boyne Pollard | last post by:
MThe library functions which are included to allow process Mlaunch, forking, and termination, imply that it is both Mpossible and desirable for a process to fork itself. This is Ma fundamental...
11
by: sunnyalways4u2000 | last post by:
hello sir, Sir will please tell me the exact difference between C and advanced C...what are the extra features or funcions...etc added in this advanced one.
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
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
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
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,...

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.