Locally compiled c++ code is improperly looping - c++

The following never terminates on my system.
#include <iostream>
using namespace std;
int main(){
int solutions[1000][4] = {};
for(int a=0; 3*a<=1000; a++){
for(int b=0; 5*b<=1000; b++){
for(int c=0; 7*c<=1000; c++){
cout << "enter" << "\t" << a << "\t" << b << "\t" << c << endl;
if (3*a+5*b+7*c > 1000) {break;}
solutions[3*a+5*b+7*c][0] = a;
solutions[3*a+5*b+7*c][1] = b;
solutions[3*a+5*b+7*c][2] = c;
solutions[3*a+5*b+7*c][3] = 1;
cout << "exit" << "\t" << a << "\t" << b << "\t" << c << endl << endl;
}
}
}
}
I'm completely stumped, so I decided to print a log of variable changes. It makes it to 4 iterations of b, and then when c hits 140, it loops back to 0. Log looks like this
...
enter 0 4 137
exit 0 4 137
enter 0 4 138
exit 0 4 138
enter 0 4 139
exit 0 4 139
enter 0 4 140
exit 0 4 0
enter 0 4 1
exit 0 4 1
enter 0 4 2
exit 0 4 2
enter 0 4 3
exit 0 4 3
...
I compiled this using g++ B.cpp -o B.exe, and then just ran the executable. The exact code (with logging commented out) terminates properly online at http://cpp.sh/. My compiler version is g++ (i686-posix-dwarf-rev0, Built by MinGW-W64 project) 5.3.0. What could be going wrong here?

When a = 0, b = 4, c = 140, 3*a+5*b+7*c becomes 1000 and write to out-of-bounds solution[1000] happens. It seems this out-of-bound write happened to break the loop counter.
Allocate one more element to avoid this out-of-bounds write.
int solutions[1001][4] = {};

Related

Trouble tracking recursive function

I have this code which outputs: 10 5 16 8 4 2 11
However, I don't have any clue from where the 11 is coming from since when tracing i get the following:
H(10)
H(5)
1+H(16) //does this result in 17?
H(8)
H(4)
H(2)
H(1) -> returns 0
Moreover what happens to the (1) in 1+H(16) ?
Thus shouldnt my output of the n values be: 10 5 17 8 4 2 1
#include <iostream>
using namespace std;
int H ( int n ) {
cout << " " << n<<" ";
if ( n == 1 ) return 0;
if ( n%2 != 0 ) return 1 + H ( 3*n + 1 );
else return H ( n/2 );
}
int main() {
// for ( int i=0; ++i<=20; )
// cout << H(i) << endl;
cout << H(10) << endl;
}
At the end of the recursion, the function prints 1 then the stack pops everything out and the main prints the returned value 1 (0 is returned at the end of the recursion and only the call to H(5) adds one to the result), so 11 is printed.

C++ define preprocessor

I am learning C++ and right we are covering preprocessors but I am trying to solve a question from a quiz which I has confused me a bit or a lot.. I tried to worked out by my own before running the program.. and my output was..
System started...
Data at 2 is: 27 28 29 30
Data at 1 is: 23 24 25 26
The data is: 19
I checked the program in Xcode to see if my output is right but the right output is the next one:
System started...
Data at 1 is: 0 0 0 19
Data at 0 is: 7 0 0 0
The data is: 19 0 0 0
This is the code...
#include <iostream>
namespace test{
#define COMPILE_FAST
#define PRINT_SPLIT(v) std::cout << (int)*((char*)(v)) << ' ' << \
(int)*((char*)(v) + 1) << ' ' << (int)*((char*)(v) +2) << ' ' << \
(int)*((char*)(v) + 3) << std::endl
typedef unsigned long long uint;
namespace er{
typedef unsigned int uint;
}
void debug(void* data, int size = 0){
if(size==0){
std::cout << "The data is: ";
PRINT_SPLIT(data);
} else {
while(size--){
std::cout << "Data at " << size << " is: ";
char* a = (char*)data;
PRINT_SPLIT((a + (4+size)));
}
}
}
}// End of Test namespace...
int main(){
test::uint a = 19;
test::er::uint b[] = {256,7};
std::cout << "System started..." << std::endl;
test::debug(b,2);
test::debug(&a);
std::cout << "Test complete";
return 0;
}
My big doubt or what I actually don't understand is whats going on here in this preprocessor because clearly for what I did its totally wrong...
#define PRINT_SPLIT(v) std::cout << (int)*((char*)(v)) << ' ' << \
(int)*((char*)(v) + 1) << ' ' << (int)*((char*)(v) +2) << ' ' << \
(int)*((char*)(v) + 3) << std::endl
if someone can be so nice and give me a brief explanation I will extremely appreciate it.
The macro prints the values (as ints) of 4 consecutive bytes. It allows you to see how a 4 byte int is layed out in memory.
Memory contents, by byte, look like this (base10):
0x22abf0: 0 1 0 0 7 0 0 0
0x22abf8: 19 0 0 0 0 0 0 0
0 1 0 0 is 256, i.e. b[0]
7 0 0 0 is 7, i.e b[1]
19 0 0 0 0 0 0 0 is 19, i.e. a
The sizeof(a) is different than the sizeof(b[0]) because there are 2 different typedefs for uint. Namely, test:uint and test::er::uint.
The address of a is greater than the address of b[] even though b is declared after a because the stack is growing downwards in memory.
Finally, I would say the output represents a defective program because the output would more reasonably be:
System started...
Data at 1 is: 7 0 0 0
Data at 0 is: 0 1 0 0
The data is: 19 0 0 0
To get that output the program needs to be changed as follows:
while(size--){
std::cout << "Data at " << size << " is: ";
int* a = (int*)data;
PRINT_SPLIT((a + (size)));

Why are addresses of vector elements not consecutive when assigned using push_back()?

Please look at the small test code + output provided below. It seems that when using push_back() on an std::vector within a loop, C++ allocates the memory at 'random' addresses, and then re-copies the data into consecutive memory addresses after the loop is finished.
Is this to do with the fact that the size of the vector is not known before the loop?
What is the correct way of doing what I do in the test code? Do I have to assign the pointers in another loop after the first one exits? Note that I cannot define the size of the vector before the first loop, because in reality it is actually a vector of class objects that require initialization.
Thank you for your help.
std::vector<int> MyVec;
std::vector<int *> MyVecPtr;
for (int i = 0; i < 10; i++)
{
MyVec.push_back(i);
MyVecPtr.push_back(&MyVec.back());
std::cout << MyVec.back() << " "
<< &MyVec.back() << " "
<< MyVecPtr.back() << " "
<< *MyVecPtr.back() << std::endl;
}
std::cout << std::endl;
for (int i = 0; i < MyVec.size(); i++)
{
std::cout << MyVec[i] << " "
<< &MyVec[i] << " "
<< MyVecPtr[i] << " "
<< *MyVecPtr[i] << std::endl;
}
0 0x180d010 0x180d010 0
1 0x180d054 0x180d054 1
2 0x180d038 0x180d038 2
3 0x180d03c 0x180d03c 3
4 0x180d0b0 0x180d0b0 4
5 0x180d0b4 0x180d0b4 5
6 0x180d0b8 0x180d0b8 6
7 0x180d0bc 0x180d0bc 7
8 0x180d140 0x180d140 8
9 0x180d144 0x180d144 9
0 0x180d120 0x180d010 25219136
1 0x180d124 0x180d054 0
2 0x180d128 0x180d038 2
3 0x180d12c 0x180d03c 3
4 0x180d130 0x180d0b0 4
5 0x180d134 0x180d0b4 5
6 0x180d138 0x180d0b8 6
7 0x180d13c 0x180d0bc 7
8 0x180d140 0x180d140 8
9 0x180d144 0x180d144 9
If you know how many insertions you will be performing, you should use reserve() on your vector accordingly. This will eliminate the need for any resizing it would otherwise perform when the capacity is exceeded.
MyVec.reserve(10);
for (int i = 0; i < 10; i++)
{
MyVec.push_back(i);
//...

Converting base 10 to 12, having trouble adding alphabet characters recursivly

I'm having trouble using recursion to add letters to a base 10 - base 12 conversion. How would I go about adding letters into my function? I was thinking about adding an if statement in, but i have no idea where and how to go about this. pointers are appreciated Thanks!
Given a count from 1 to 12:
Dec 1 2 3 4 5 6 7 8 9 10 11 12
Duo 1 2 3 4 5 6 7 8 9 X E 10
my function:
template<class myType>
myType convertDec(myType number){
if(number == 0)
return number;
//if statement somewhere in here? not sure considering i can't touch the return statement
return (number % 12) + 10*convertDec(number / 12);
}
example ideal output:
65280 = 31940 (works fine)
2147483626 = 4EE23088X (doesnt work!)
#include <iostream>
#include <string>
using namespace std;
string ConvertToDuodecimal(unsigned long long n)
{
if (n < 12)
return string() + "0123456789XE"[n];
return ConvertToDuodecimal(n / 12) + ConvertToDuodecimal(n % 12);
}
int main()
{
cout << ConvertToDuodecimal(0) << endl;
cout << ConvertToDuodecimal(1) << endl;
cout << ConvertToDuodecimal(10) << endl;
cout << ConvertToDuodecimal(11) << endl;
cout << ConvertToDuodecimal(12) << endl;
cout << ConvertToDuodecimal(13) << endl;
cout << ConvertToDuodecimal(65280) << endl;
cout << ConvertToDuodecimal(2147483626) << endl;
return 0;
}
Output (ideone):
0
1
X
E
10
11
31940
4EE23088X
The base is a property of the way a number is displayed and nothing to do with it's internal representation. You need to write a function that prints a normal int using base 12.
a = 12; // A = 12 (in base 10)
printf("%d",a); // Prints a in base 10 (still 12)
printf("%x",a); // Prints a in base 16 (now C)
You code is changing the actual value, which isn't the right thing to do.
(and yes, before the pedants strike, printf isn't good C++...)

OpenMP - parallel code has unexpected results

#include "/usr/lib/gcc/i686-linux-gnu/4.6/include/omp.h"
#include <iostream>
#include<list>
using namespace std;
int main()
{
list<int> lst;
for(int i=0;i<5;i++)
lst.push_back(i);
#pragma omp parallel for
for(int i=0;i<5;i++)
{
cout<<i<<" "<<omp_get_thread_num()<<endl;
}
}
suppose that I can get this:
0 0
1 0
2 0
3 1
4 1
However, sometimes I can get this result:
30 0
1 0
2 0
1
4 1
or even this kind of result:
30 1 0
4 1
1 0
2 0
I know this is because the output code:
cout<<i<<" "<<omp_get_thread_num()<<endl;
has been spliced into small segments and has no order when doing output.
But who can tell me how to prevent this from happening?
Thanks.
Standard output streams are NOT synchronized!
The only guarantee the standard gives is that, single characters are outputted atomically.
You need either a lock - which defies the point of parallelization or you could drop the "<< i" which should result in a quasi synchronized behavior.
The loop runs out of order. This is why you have unordered output.
If your problem is the 30 in
30 0
1 0
2 0
1
4 1
then stay cool, there is no 30, but 3 and 0. You still have, as expected, an unordered row of [0..4]:
3 0 0
1 0
2 0
1
4 1
What you can't tell is only which of the 0s which of the 1s is not a thread number.
Your code
#pragma omp parallel for
for(int i = 0; i < 5; i++)
{
cout << i << " " << omp_get_thread_num() << endl;
}
is equivalent to
#pragma omp parallel for
for(int i = 0; i < 5; i++)
{
cout << i;
cout << " ";
cout << omp_get_thread_num();
cout << endl;
}
Calls to << in the different threads may be executed in any order. For instance cout << i; in thread 3 may be followed by cout << i; in tread 0 which may be followed by cout << " "; in thread 3 etc. resulting in the garbled output 30 ....
The correct way is to rewrite the code so that each thread calls cout << only once in the loop:
#pragma omp parallel for
for(int i = 0; i < 5; i++)
{
stringstream ss;
ss << i << " " << omp_get_thread_num() << '\n';
cout << ss.str();
}
You can create an array (of size 5) containing which thread handled which index and then print it outside the parallel loop.