It's more trickier than I primarly thinked.
Okay, so lets say you have "n" uniq element.
The total amout of uniq possibility is "n!" (so for 5 element, you have 120 possibility).
Let's say you want to make "group" of "k" number.
So if n = 5 and k = 2, you end up with your example :
{0, 1}, {2, 3}, {4}.
Now, that's where the fun begin :
In order to know if the current proposition is not a duplicate, you can discard every proposition for which the first number in every complete group is not sorted.
for example :
{0, 1}, {2, 3}, {4}.
here, 1 and 3 are useless because that not the first value of a complete group, and 4 is part of an incomplete group.
So what is interesting is
{0, ?}, {2, ?}, {?}.
Is 0, 2 sorted ? Yes, so you can keep this proposition.
That means that if you have
{2, 3}, {0, 1}, {4}.
It's no good, because
{2, ?}, {0, ?}, {?}.
2, 0 is not sorted.
If you have n = 6 and k = 2, then is
{0, 2}, {3, 4}, {1, 5}
valid ? No, because 0 3 1 is not sorted.
And you can see that
{0, 2}, {1, 5} , {3, 4}
is the valid sorted proposition.
Now, is there a possibility to calculate how many valid proposition we will have if we know n and k ?
Yes.
Maybe.
I think ...
I will update if I can found something.
Edit :
Aaaaaannnd, here an implementation. A little fun to do ...
It based on the previous algorithm, so of course if my algorithm is false, then this code is false.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define N 5
#define K 2
void Comb_Display(int proposition[N])
{
printf("{");
for (int i = 0; i < N; ++i) {
if (i && i % K == 0) {
printf("} {");
}
printf("%d%s", proposition[i], (i && (i + 1) % K == 0) || i + 1 >= N ? "" : ", ");
}
printf("}\n");
}
bool Comb_Valid(int proposition[N])
{
int nbGroup = N / K;
if (nbGroup == 1) {
return (true);
}
for (int i = 0; i < nbGroup; i += K) {
if (proposition[i] > proposition[i + K]) {
return (false);
}
}
return (true);
}
void Comb_MakeMagicPlease(int numberAvailable[N], int proposition[N], int ind)
{
// We are at the end of the array, so we have a proposition
if (ind >= N) {
printf("%s : ", Comb_Valid(proposition) ? "OK" : " "); // O = Valide, ' ' = invalide
Comb_Display(proposition);
return;
}
// We scan "numberAvailable" in order to find the first number available
for (int i = 0; i < N; i++) {
if (numberAvailable[i] != -1) {
int number = numberAvailable[i];
numberAvailable[i] = -1; // We mark the number as not available
proposition[ind] = number;
Comb_MakeMagicPlease(numberAvailable, proposition, ind + 1);
numberAvailable[i] = number; // we mark the number as available
}
}
}
int main(void)
{
int numberAvailable[N];
int proposition[N];
for (int i = 0; i < N; ++i) {
numberAvailable[i] = i + 1;
}
Comb_MakeMagicPlease(numberAvailable, proposition, 0);
return 0;
}