Related
I am extremely new to the coding world. I just have a basic question regarding this function that squares integers from 0-9. I understand most of what's going on until I get to
std::cout << i << " " << square << "\n";
i = i + 1;
I'm not too sure how that ends up causing the output to square the results in order from 0-9. Can someone explain the reasoning behind this line of code? Here is the code for this function.
#include <iostream>
int main() {
int i = 0;
int square = 0;
while ( i <= 9) {
square = i*i;
std::cout << i << " " << square << "\n";
i = i + 1;
}
return 0;
}
This code:
std::cout << i << " " << square << "\n";
i = i + 1;
Doesn't square anything. It is merely outputting the current square that has already been calculated, and then increments i for the next loop iteration.
The actual squaring happens here:
square = i*i;
So, the code starts at i=0, calculates square=0*0 and displays it, then sets i=1, calculates square=1*1 and displays it, then sets i=2, calculates square=2*2 and displays it, and so on until i exceeds 9, then the loop stops.
Lets start from beginning and what is happening, I will ignore first several lines and start at:
int i = 0;
int square = 0;
You see when you say int i; your compiler says I need to allocate bucket of memory to hold value for i. When you say i = 0 zero is put into that memory bucket. That is what is happening for square as well.
Now to loop
while ( i <= 9 ) {
square = i*i;
std::cout << i << " " << square << "\n";
i = i + 1;
}
So, lets ignore
square = i*i;
std::cout << i << " " << square << "\n";
for now we will come to it later.
So
while ( i <= 9 ) {
i = i + 1;
}
goes into the loop and gets value from i's bucket, adds 1 and puts new value into the i's bucket. So in first loop it will be i = 0 + 1, put 1 into i bucket. Second, i = 1 + 1 put 2 in, third i = 2 + 1 put 3.
So lets go back to square and its bucket.
square = i*i;
So first time we go into the loop i = 0 and square = 0 * 0 so compiler puts 0 into square's memory bucket. Next time it hits square i has been incremented to 1 so square = 1 * 1, thus compiler puts 1 into the bucket. Third time i is 2 so square = 2 * 2, and compiler puts 4 into the bucket. And so on till it i <= 9. When i hits 10 loop is not executed.
In comments you have stated that you do not know the difference between a math equation and an assignment statement. You are not alone.
I will try to explain, as an addition to existing answers, to provide a different angle.
First, two examples of math equations:
x = 1 +1
y+1 = x*2
To illustrate their meaning, let me point our that you first can determine that x is 2 and in a second step that y is 3.
Now examples of assignment statements.
x = 1 +1;
y = x*2;
The minor difference is the ; at the end, tipping you off that it is a program code line.
Here the first one looks pretty much the same as the first equation example. But for a C compiler this is different. It is a command, requesting that the program, when executing this line, assigns the value 2 to the variable x.
The second assingment statement I made similar to the second equation example, but importantly different, because the left side of = is not an expression, not something to calculate. The equation-turned-statement
y +1 = x*2;
does not work, the compiler will complain that it cannot assign a value (no problem with doing a little calculation on the right side) to an expression. It cannot assign the value 4 to the expression y+1.
This helps with your problem, because you need to understand that both lines
i = i + 1;
square = i*i;
are statements which, when executed (and only then) cause a change to the value of the variable in that line.
Your program starts off with the value 0 in the variable i. At some point it executes the first of the statements above, causing the value of i to change from 0 to 1. Later, when the same line is executed again, the value of i changes from 1 to 2. So the values of i change, loop iteration by loop iteration, to 2,3,4,5,6,7,8,9
The second assignment line causes the value of square to become the value of i, whatever it is during that loop iteration and multiplied by itself. I.e. it gets to be 4,9,16,25,36....
Outputting the value of square each time in the loop gets you the squares.
Since you state that you basically understand loops, I just mention that the loop ends when i is not lower or equal to 9 any more.
Now from the other point of view.
If you try to solve the equation
i = i + 1
for i, you should hear your math teacher groaning.
You can subtract i from both sides and get
0 = 1
The solution is "Don't try.", it is not an equation.
std::cout << i << " " << square << "\n"; prints every
number i next to its square, which is previously computed
(square = i*i;).
i = i + 1; increments i to compute the next square. It stops when i reaches 10.
The output will look like this:
0 0
1 1
2 4
3 9
4 16
5 25
6 36
7 49
8 64
9 81
So we have a while loop here, which run while i <= 9. The square of any number i is i * i.
while(i <=9){ //check the condition and then enter the body
//body
}
But we need a condition to get out of the loop, otherwise our program will enter into an infinite loop.
To ensure, we will exit from the loop we increase the value of i by 1.
so at first when i = 0 square = 0 * 0 = 0,now we increase the value of i i.e now i becomes one which still satisfies the condition to stay inside the loop , again it will calculate square = 1 * 1 until and unless the value of i remains less than or equal to 9.
Once the condition fails, the execution comes out of the loop.
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 7 years ago.
Improve this question
I am a noob programmer,who just started in C++. I wrote a program, to answer a question. When I try to run it from my cmd.exe, windows tells me "a problem has caused this program to stop working, we'll close the program and notify you when a solution is available".
I have included a link to the well documented source code. Please take a look at the code, and help me out.
link: http://mibpaste.com/ZRevGf
i believe, that figuring out the error, with my code may help several other noob programmers out there, who may use similar methods to mine.
Code from link:
//This is the source code for a puzzle,well kind of that I saw on the internet. I will include the puzzle's question below.
//Well, I commented it so I hope you understand.
//ALAFIN OLUWATOBI 100L DEPARTMENT OF COMPUTER SCIENCE BABCOCK UNIVERSITY.
//Future CEO of VERI Technologies inc.
/*
* In a corridor, there are 100 doors. All the doors are initially closed.
* You walk along the corridor back and forth. As you walk along the corridor, you reverse the state of each door.
* I.e if the door is open, you close it, and if it is closed, you open it.
* You walk along the corrdor, a total of 200 times.
* On your nth trip, You stop at every nth door, that you come across.
* I.e on your first trip, you stop at every door. On your second trip, every second door, on your third trip every third door and so on and so forth
* Write a program to display, the final states of the doors.
*/
#include <iostream>
#include <cstdlib>
#include <cmath>
using namespace std;
inline void inverse(bool args[]); //The prototype of the function. I made the function inline in the declaration, to increase efficiency, ad speed of execution.
bool doors [200]; //Declaring a global array, for the doors.
int main ()
{
inverse(doors); //A call to the inverse function
cout << "This is the state of the 100 doors...\n";
for (int i = 0 ; i<200 ; i++) //Loop, to dis play the final states of the doors.
{
cout << "DOOR " << (i+1) << "\t|" << doors[i] << endl;
}
cout << "Thank you, for using this program designed by VERI Technologies. :)"; //VERI Technologies, is the name of the I.T company that I hope to establish.
return 0;
}
void inverse(bool args [])
{
for (int n = 1 ; n<= 200 ; n++) //This loop, is for the control of every nth trip. It executes 100 times
{
if (n%2 != 0) //This is to control the reversal of the doors going forward, I.e on odd numbers
{
for (int b = n, a = 1 ; b<=200 ;b = n*++a) //This is the control loop, for every odd trip, going forwards. It executes 100 times
args [b] = !args[b] ; //The reversal operation. It reverses the boolean value of the door.
}
/*
* The two variables, are declared. They will be used in controlling the program. b represents the number of the door to be operated on.
* a is a variable, which we shall use to control the value of b.
* n remains constant for the duration, of the loop, as does (200-n)
* the pre increment of a {++a} multiplied by n or (200-n) is used to calculate the value of b in the update.
* Thus, we have the scenario, of b increasing in multiples of n. Achieving what is desired for the program. Through this construct, only every nth door is considered.
*/
else if((n%2) == 0) //This is to control the reversal of the doors going backwards, I.e on even numbers
{
for (int b = (200-n), a = 1 ; b>=1 ; b = (200-n)*++a) //This is the control loop for every even trip, going backwards. It executes 100 times.
args [b] = !args[b] ; //The reversal operation. It reverses the boolean value of the door.
}
}
}
I believe the exception is due to the line:
for (int b = (200 - n), a = 1; b >= 1; b = (200 - n)*++a)
When the exception occurs the following values are assigned to the variables:
b = 3366
n = 2
a = 17
From what I can see, b is calculated by (200 - n) * a.
If we substitute the values given we have: 198 * 17
This gives us the value of 3366 which is beyond the index of doors and throws the exception when the line
args[b] = !args[b];
is executed.
I have created the following solution that should provide the desired results if you wish to use it.
void inverse(bool args[])
{
//n represents what trip you are taking down the hallway
//i.e. n = 1 is the first trip, n = 2 the second, and so on
for (int n = 1; n <= 200; n++){
//We are on trip n, so now we must change the state of all the doors for the trip
//The current door is represented by i
//i.e. i = 1 is the first door, i = 2 the second, and so on
for (int i = 1; i <= 200; i++){
//If the current door mod the trip is 0 then we must change the state of the door
//Only the nth door will be changed which occurs when i mod n equals 0
//We modify the state of doors[i - 1] as the array of doors is 0 - 199 but we are counting doors from 1 to 200
//So door 1 mod trip 1 will equal 0 so we must change the state of door 1, which is really doors[0]
if (i % n == 0){
args[i - 1] = !args[i - 1];
}
}
}
EUREKA!!!!!!
I finally came up with a working solution. No more errors. I'm calling it version 2.0.0
I've uploaded it online, and here's the link
[version 2.0.0] http://mibpaste.com/3NADgl
All that's left is to go to excel, and derive the final states of the door and be sure, that it's working perfectly. Please take a look at my solution, and comment on any error that I may have made, or any way you think that I may optimize the code.I thank you for your help, it allowed me to redesign a working solution to the program. I'm sstarting to think that an Out-of-bounds error, might have caused my version 1 to crash, but the logic was flawed, anyway, so I'm scrapping it.
This is ths code:
/**********************************************************************************************
200 DOOR PROGRAM
Version 2.0.0
Author: Alafin OluwaTobi Department of Computer Science, Babcock University
New Additions: I redrew, the algorithm, to geneate a more logically viable solution,
I additionally, expanded the size of the array, to prevent a potential out of bounds error.
**********************************************************************************************/
//Hello. This a program,I've written to solve a fun mental problem.
//I'll include a full explanation of the problem, below.
/**********************************************************************************************
*You are in a Hallway, filled with 200 doors .
*ALL the doors are initially closed .
*You walk along the corridor, *BACK* and *FORTH* reversing the state of every door which you stop at .
*I.e if it is open, you close it .
*If it is closed, you open it .
*On every nth trip, you stop at every nth door .
*I.e on your first trip, you stop at every door. On your second trip every second door, On your third trip every third door, etc .
*Write a program to display the final state of the doors .
**********************************************************************************************/
/**********************************************************************************************
SOLUTION
*NOTE: on even trips, your coming back, while on odd trips your going forwards .
*2 Imaginary doors, door 0 and 201, delimit the corridor .
*On odd trips, the doors stopped at will be (0+n) doors .
*I.e you will be counting forward, in (0+n) e.g say, n = 5: 5, 10, 15, 20, 25
*On even trips, the doors stopped at will be (201-n) doors.
*I.e you will be counting backwards in (201-n) say n = 4: 197, 193, 189, 185, 181
**********************************************************************************************/
#include <iostream>
#include <cstdlib> //Including the basic libraries
bool HALLWAY [202] ;
/*
*Declaring the array, for the Hallway, as global in order to initialise all the elements at zero.
*In addition,the size is set at 202 to make provision for the delimiting imaginary doors,
*This also serves to prevent potential out of bound errors, that may occur, in the use of thefor looplater on.
*/
inline void inverse (bool args []) ;
/*
*Prototyping the function, which will be used to reverse the states of the door.
*The function, has been declared as inline in order to allow faster compilation, and generate a faster executable program.
*/
using namespace std ; //Using the standard namespace
int main ()
{
inverse (HALLWAY) ; //Calling the inverse function, to act on the Hallway, reversing the doors.
cout << "\t\t\t\t\t\t\t\t\t\t200 DOOR TABLE\n" ;
for(int i = 1 ; i <= 200 ; i++ )
//A loop to display the states of the doors.
{
if (HALLWAY [i] == 0)
//The if construct allows us to print out the state of the door as closed, when the corresponding element of the Array has a value of zero.
{
cout << "DOOR " << i << " is\tCLOSED" << endl ;
for (int z = 0 ; z <= 300 ; z++)
cout << "_" ;
cout << "\n" ;
}
else if (HALLWAY [i] == 1)
//The else if construct allows us to print out the state of the door as open, when the corresponding element of the Array has a value of one.
{
cout << "DOOR " << i << " is\tOPEN" << endl ;
for (int z = 0 ; z <= 300 ; z++)
cout << "_" ;
cout << "\n" ;
}
}
return 0 ; //Returns the value of zero, to show that the program executed properly
}
void inverse (bool args[])`
{
for ( int n = 1; n <= 200 ; n++)
//This loop, is to control the individual trips, i.e trip 1, 2, 3, etc..
{
if (n%2 == 0)
//This if construct, is to ensure that on even numbers(i,e n%2 = 0), that you are coming down the hallway and counting backwards
{
for (int b = (201-n) ; b <= 200 && b >= 1 ; b -= n)
/*
*This loop, is for the doors that you stop at on your nth trip.
*The door is represented by the variable b.
*Because you are coming back, b will be reducing proportionally, in n.
*The Starting value for b on your nth trip, will be (201-n)
* {b -= n} takes care of this. On the second turn for example. First value of b will be 199, 197, 195, 193, ..., 1
*/
args [b] = !(args [b]) ;
//This is the actual reversal operation, which reverses the state of the door.
}
else if (n%2 != 0)
//This else if construct, is to ensure that on odd numbers(i.e n%2 != 0), that you are going up the hallway and counting forwards
{
for (int b = n ; b <= 200 && b >= 1 ; b += n)
/*
*This loop, is for the doors that you stop at on your nth trip.
*The door is represented by the variable b.
*Because you are going forwards, b will be increasing proportionally, in n.
*The starting value of b will be (0+n) whch is equal to n
* {b += n} takes care of this. On the third turn for example. First value of b will be 3, 6, 9, 12, ...., 198
*/
args [b] = !(args [b]) ;
//This is the actual reversal operation, which reverses the state of the door
}
}
}
In the C++ Standard std:string follows an exponential growth policy, therefore I suppose the capacity() of string during concatenation will always be increased when necessary. However, when I test test.cpp, I found that in the for-loop, only every two times will the capacity() be shrunk back to length() during assignment.
Why isn't this behavior depending on the length of string, but depending on how frequent I change the string? Is it some kind of optimization?
The following codes are tested with g++ -std=c++11.
test.cpp:
#include <iostream>
int main(int argc, char **argv) {
std::string s = "";
for (int i = 1; i <= 1000; i++) {
//s += "*";
s = s + "*";
std::cout << s.length() << " " << s.capacity() << std::endl;
}
return 0;
}
And the output will be like this:
1 1
2 2
3 4
4 4
5 8
6 6 // why is capacity shrunk?
7 12
8 8 // and again?
9 16
10 10 // and again?
11 20
12 12 // and again?
13 24
14 14 // and again?
15 28
16 16 // and again?
17 32
...
996 996
997 1992
998 998 // and again?
999 1996
1000 1000 // and again?
When you do this:
s = s + "*";
You're doing two separate things: making a new temporary string, consisting of "*" concatenated onto the end of the contents s, and then copy-assigning that new string to s.
It's not the + that's shrinking, it's the =. When copy-assigning from one string to another, there's no reason to copy the capacity, just the actual used bytes.
Your commented-out code does this:
s += "*";
… is only doing one thing, appending "*" onto the end of s. So, there's nowhere for the "optimization" to happen (if it happened, it would be a pessimization, defeating the entire purpose of the exponential growth).
It's actually not convered by the C++ standard what happens to capacity() when strings are moved, assigned, etc. This could be a defect. The only constraints are those derivable from the time complexity specified for the operation.
See here for similar discussion about vectors.
I am using MongoDB 2.4.5 64 bit on Linux using C++ API to insert 1 M record
I did turn on write concern after the connection
mongo.setWriteConcern(mongo::W_NORMAL);
for (int i=0; i<RECORDS; i++) {
mongo::BSONObj record = BSON (
"_id" << i <<
"mystring" << "hello world" );
bulk_data.push_back(record);
if (i % 10000 == 0) {
mongo.insert("insert_test.col1", bulk_data);
}
}
Surprisingly at the end when I do count (via count(), it only shows 990001 records from collection 'insert_test.col1'.
What did I do wrong? Thanks for your help.
You're missing mongo.insert("insert_test.col1", bulk_data); at the end of (immediately after) your loop -- unless RECORDS is one less than a multiple of 10000 (you said it was 1000000, which isn't), then the last 9999 iterations are not inserted because they're still in bulk_data!
In other words, i is only 999999 on the last iteration through the loop, so the if isn't entered, and the last 9999 records that were put in bulk_data are not inserted.
Also, bulk_data needs to be cleared after being inserted:
if (i % 10000 == 0) {
mongo.insert("insert_test.col1", bulk_data);
bulk_data.clear(); // <-----
}
I have a vector of structs, with the structs looking like this:
struct myData{
int ID;
int arrivalTime;
int burstTime;
};
After populating my vector with this data:
1 5 16
4 7 12
3 12 4
2 7 8
where each row is an individual struct's ID (arbitrary, doesn't denote order of arrival), arrivalTime and burstTime, how would I use "for" or "while" loops to step through my vector's indices and calculate the data in a way that I could print something like this out?
Time 0 Processor is Idle
Time 5 Process 1 starts running
Time 21 Process 2 is running
Time 29 Process 4 is running
Time 41 Process 3 is running
The way I thought I could do it was to have an integer keep track what the current time is (the current time being the sum of the burst times of processes that have already ran) but I can't seem to figure out an algorithm that accounts for Idle time (when the processor is not doing anything and a new task hasn't arrived yet) as well as keeping track of the other numbers as well. For simplicity's sake I just decided that when two processes arrive at the same time I would process the one with the lower ID number. I know I didn't put much code here to demonstrate what I'm trying to do, but I hope I've explained it fairly clearly. I'm looking for a psuedo-code algorithm solution to this problem, but I wouldn't say no to something that has been coded (In C++?).
As an additional note, in case I wasn't able to convey how I access my data clearly, this:
cout << structVector[0].ID << "\n";
cout << structVector[0].arrivalTime << "\n";
cout << structVector[0].burstTime << "\n";
would print out
1
5
16
Any help in psuedo-code or actual code would be GREATLY appreciated!!! After reading this post over a few times I realize I've been pretty generic with the question, but I would love some help just understanding how to calculate this data.
First, sort the vector based on arrival times.
Then the following code will accomplish what you are looking for.
int i = 0, time = 0;
while (i < vec.size())
{
if (vec[i]. arrivalTime > time)
cout << "Time " << time << "process is idle";
time += vec[i].arrivalTime;
cout << "Time " << time << " Process " << vec[i].ID << " is running" << endl;
time += vec[i].burstTime;
i++;
}