You are here:

# C++/nested looping

Question
hi! I know the basics of looping, but would like to do this..

ex:

input number : 10

output:

1234 10 5678 26 910 19

and this is the code i came up with..
----------------------------------------------
#include <iostream.h>
#include <conio.h>
int main()
{
clrscr();
int n,s,x=0,sum=0,num=0,num1;
cin>>n;
do
{
s=1;
sum=0;
while ((s<=4)&&(num<=n))
{
num=x+s;
cout<<num;
sum+=num;
s++;
}
cout<<" "<<sum<<" ";
x=num;
}
while (num<=n);

getch();
return 0;
}
------------------------

however..
when i input let's say 5,
its output looks something like this..

1234 10 56 11

or

input : 10

1234 10 5678 26 91011 30

--

it should stop when "num" becomes equal to the input "n" right? (atleast thats what i thought) what am i doing wrong here?

thank you so much..

I am not going to just tell you where you went wrong. Instead I am going to ask you some questions and show you parts of your code to consider to help get you looking and thinking in the right direction and then show you an alternate solution that I hope is easier to reason about.

OK, here goes...

I would start by considering your last statement if I were you and look at your code carefully.

When do you update (and then use) num such that it becomes equal to n in relation to where you test for num to see if the end of the range has been reached?

Or to put it another way: is the value of num used for output to the user and for inclusion in sum values the same value of num as was tested for loop termination just previously?

Start by considering these lines:

while ((s<=4)&&(num<=n))
{
num=x+s; // assume this is similar to ++num
cout<<num;

If when tested in the first line s is 1, 2, 3 or 4 and num is equal to n, so the loop continues, what value of num will be reported to the user in the third line?

Is this the same value as was tested for in the first line? If not what is the difference and how could you change the test: num<=n so that the correct range of values is reported?

Hint: you start num with a value of 0, which is tested for by num<=n but your code is only supposed to start writing and summing values from 1...so is the value printed and summed (e.g. 1) the same as that that was just tested (e.g. 0)?

I am fairly sure your solution is a bit overly complex - for one, I am not really sure I would have bothered with nested loops for a solution to this problem - unless I were specifically asked to do so. I would use a for loop to iterate through the range of numbers of interest and get that right, then add in some extra logic to cater for the sum values. As a code fragment it might start out like so (using ISO standard C++ - hence the std:: qualifications on cout, cin and cerr):

unsigned int const min(2);
unsigned int const max(20);
unsigned int const range_begin(1);
unsigned int range_end(max+1);

std::cout << "Enter range end in the range [" << min << "," << max << "]: ";
std::cin>>range_end;
if (min > range_end || range_end > max)
{
std::cerr << "Entry error: " << range_end << " is out of range.\n";
return 1;
}

for (unsigned int n=range_begin; n<=range_end; ++n)
{
std::cout << n;
// sum code goes here...
}
std::cout << std::endl;

return 0;

Notes:
- the use of named constant values for 'magic numbers' min, max and range_begin
- the checking of the input value - should also check that std::cin is good as well but I shall leave that out for
brevity and as an exercise!
- the use of a single for loop to generate the values to be output and summed in groups.

Adding in the summing code, which replaces the for loop in the previous code fragment:

unsigned int const sum_grouping(4);
unsigned int sum(0);
for (unsigned int n=range_begin; n<=range_end; ++n)
{
std::cout << n;
sum += n;
if (0==n%sum_grouping || n==range_end)
{
std::cout << ' ' << sum << ' ';
sum = 0;
}
}

Notes:
- again the use of a named constant value for the grouping period value for summation
- sum printing and resetting is done whenever n is divisible by the sum_grouping value (4 here) with no remainder.
For this the modulus operator % is used, which is the other half of integer division - the result is the remainder
rather than the division value, hence 1 % 4 = 1, 3 % 4 = 3, 4 % 4 = 0, 6 % 4 = 2 and 8 % 4 = 0, etc...
- the sum also has to be printed on the last iteration of the for loop whatever the current sum group count is, which
is taken care of by the n==range_end part of the if test expression - we print and reset the sum if either or both
the modulus test or n==range_end test are true and hence we combine the two tests with a Boolean OR operator ||.

My hope, as I said at the start, is that you will find my example code a bit easier to reason about than your original code - this is one of the main points about code - always try for as clear an approach as possible - it will help stop you going nuts trying to keep track of what is going on! Sometimes we get a working solution after some tinkering and the tinkering has blown away any original clarity - in such cases it is best to re-work the code in a shiny new form which does the same as before but in a clearer fashion - a task known as refactoring. It helps in such cases to have a set of easy to execute tests for the code in question as you can then re-run them on the refactored code to make sure no errors crept in.

Hope this helps.
Questioner's Rating
 Rating(1-10) Knowledgeability = 10 Clarity of Response = 10 Politeness = 10 Comment thank you so much.. i have just realized my mistake when i reviewed the email sent to me confirming the question i have posted.. but thank you very much.. this is a great help.. i get to have an alternative solution aside from what i came up with.. :)

C++

Volunteer

#### Ralph McArdell

##### Expertise

I am a software developer with more than 15 years C++ experience and over 25 years experience developing a wide variety of applications for Windows NT/2000/XP, UNIX, Linux and other platforms. I can help with basic to advanced C++, C (although I do not write just-C much if at all these days so maybe ask in the C section about purely C matters), software development and many platform specific and system development problems.

##### Experience

My career started in the mid 1980s working as a batch process operator for the now defunct Inner London Education Authority, working on Prime mini computers. I then moved into the role of Programmer / Analyst, also on the Primes, then into technical support and finally into the micro computing section, using a variety of 16 and 8 bit machines. Following the demise of the ILEA I worked for a small company, now gone, called Hodos. I worked on a part task train simulator using C and the Intel DVI (Digital Video Interactive) - the hardware based predecessor to Indeo. Other projects included a CGI based train simulator (different goals to the first), and various other projects in C and Visual Basic (er, version 1 that is). When Hodos went into receivership I went freelance and finally managed to start working in C++. I initially had contracts working on train simulators (surprise) and multimedia - I worked on many of the Dorling Kindersley CD-ROM titles and wrote the screensaver games for the Wallace and Gromit Cracking Animator CD. My more recent contracts have been more traditionally IT based, working predominately in C++ on MS Windows NT, 2000. XP, Linux and UN*X. These projects have had wide ranging additional skill sets including system analysis and design, databases and SQL in various guises, C#, client server and remoting, cross porting applications between platforms and various client development processes. I have an interest in the development of the C++ core language and libraries and try to keep up with at least some of the papers on the ISO C++ Standard Committee site at http://www.open-std.org/jtc1/sc22/wg21/.

Education/Credentials