How can I make a random 4x4 array<array<int,4>,4>? Each element of this 2D array should be unique number from the interval from 0 to 15, inclusive.
Example:
6 7 5 4
10 11 12 15
1 3 2 8
9 14 0 13
Here are some steps that you could follow:
std::array<std::array<int, 4>, 4> myArray;16, that contains values from 0 to 15.for (int i = 0, k = 0; i < 4; ++i) for (int j = 0; j < 4; ++j) myArray[i][j] = values[k++];vector<int> myvector; for (int i=0; i<15; ++i) myvector.push_back(i); random_shuffle ( myvector.begin(), myvector.end() ); for (int i=0; i<15; ++i) cout << " " << myvector[i]; Why does this always print the same sequence of numbers? Why doesnt it randomise every time i run it ?Not a bad question. This would be my pick:
I extended my answer to include another (simple) solution to the problem using std::vector only, and std::vector + std::array (as asked by the O.P.).
#include <vector>
#include <array>
#include <algorithm>
using namespace std;
// ...
const int N = 4; // we want to have 4x4 arrays for now
// ...
// C++ was tremendously simplified over the years in order to
// get a much more complicated language. This is what you can do ...
// ...
// First, generate a std::vector of shuffled numbers [0..15] over 16 elements
vector<int> v;
for(int i=0; i<N*N; i++) v.push_back(v.size()); // initialize w/index
random_shuffle (v.begin(), v.end()); // shuffle element values
// (Variant 1) std::array (C++11), row-wise copy of the vector data
// + will only work with newer (C++11 enabled) compiler versions
array<array<int,N>,N> amat; // there's no assign() member, so we have
for(int i=0; i<N; i++) // to copy each row through external template
copy( v.begin()+i*N, v.begin()+(i+1)*N, amat[i].begin() );
// done
// ...
In the for loop, we only do 4 iterations but have a total of 4x4 elements. Because each of the 4 matrix rows is 4 elements wide, we have to find a way how we take the correct 4 elements for each matrix row from our shuffeld 16-element 1D vector v: v.begin()+i*N ... v.begin()+(i+1)*N. If i is 0 (first iteration), we copy the four elements from v[0 * N] ... v[0+1 * N], this means v[0] .. v[4].
This is a sequence where the last element v[4] is not included in the copy. This is also somehow an idiomatic pattern in C/C++ which is comparable to: for(i=START; i < END; i++) ....
The END element is therefore beyond the range, not included.
In the second iteration (i = 1), we have v[1 * N] ... v[1+1 * N], which is v[4] ... v[8]. You see the pattern?
// ...
// (Variant 2) std::vector (STL), row-wise copy of the vector data
// + should work with almost every c++ compiler
vector<vector<int>> vmat(N);
for(int i=0; i<N; i++)
vmat[i].assign( v.begin()+i*N, v.begin()+(i+1)*N );
// done
// ...
// TODO: now try to print all elements line 4x4 matrix
Why is the shuffled order always the same? The C library uses a random number implementation that starts from the same seed number generating always the same sequence (which might be important for debugging). In order to get different shuffling, you'd have to re-initialize the random number generator at the program start once.
...
srand((unsigned)time(NULL))
...
For this, you need the C-library time-header (for time()) and most probably stdlib-header (for srand()):
...
#include <ctime>
#include <cstdlib>
...
I deliberately tried to provide very simple solutions only. Therefore, no generators or C++11 lambdas seemed appropriate for this purpose.
Regards
rbo
array<array<int,4>,4>not constructive?