ho scritto qualche codice C++ 11 attuazione di un N- nested for-loop per me stesso. Ecco la parte principale del codice che può essere utilizzata come singola importazione .hpp (l'ho chiamata nestedLoop.HPP):
#ifndef NESTEDLOOP_HPP
#define NESTEDLOOP_HPP
#include <vector>
namespace nestedLoop{
class nestedLoop {
public:
//Variables
std::vector<int> maxes;
std::vector<int> idxes; //The last element is used for boundary control
int N=0;
int nestLevel=0;
nestedLoop();
nestedLoop(int,int);
nestedLoop(int,std::vector<int>);
void reset(int numberOfNests, int Max);
void reset(int numberOfNests, std::vector<int> theMaxes);
bool next();
void jumpNest(int theNest);
private:
void clear();
};
//Initialisations
nestedLoop::nestedLoop(){}
nestedLoop::nestedLoop(int numberOfNests, int Max) {
reset(numberOfNests, Max);
}
nestedLoop::nestedLoop(int numberOfNests, std::vector<int> theMaxes) {
reset(numberOfNests, theMaxes);
}
void nestedLoop::clear(){
maxes.clear();
idxes.clear();
N = 0;
nestLevel = 0;
}
//Reset the scene
void nestedLoop::reset(int numberOfNests, int Max){
std::vector<int> theMaxes;
for(int i =0; i < numberOfNests; i++) theMaxes.push_back(Max);
reset(numberOfNests, theMaxes);
}
void nestedLoop::reset(int numberOfNests, std::vector<int> theMaxes){
clear();
N = numberOfNests;
maxes=theMaxes;
idxes.push_back(-1);
for(int i=1; i<N; i++) idxes.push_back(theMaxes[i]-1);
}
bool nestedLoop::next(){
idxes[N-1]+=1;
for(int i=N-1; i>=0; i--){
if(idxes[i]>=maxes[i]) {
idxes[i] = 0;
if(i){ //actually, if i > 0 is needed
idxes[i-1] += 1;
}else{
return false;
}
}else{
nestLevel = i;
break;
}
}
return true;
}
void nestedLoop::jumpNest(int theNest){
for(int i = N-1; i>theNest; i--) {
idxes[i] = maxes[i]-1;
}
}
}
#endif // NESTEDLOOP_HPP
Ecco un esempio con risultati attesi:
#include <iostream>
#include "stlvecs.hpp"
#include "nestedLoop.hpp"
int main(){
nestedLoop::nestedLoop looper;
std::vector<int> maxes = {2, 3, 2, 2};
looper.reset(4,maxes);
int i = 0;
while(looper.next()){
std::cout << "Indices: " << looper.idxes << ", Last nest incremented: " << looper.nestLevel << std::endl;
if(i == 5){
std::cout << "...Jump Second Nest (index 1)..." << std::endl;
looper.jumpNest(1);
}
i++;
}
}
/* Expected output
Indices: 4 0 0 0 0 , Last nest incremented: 0
Indices: 4 0 0 0 1 , Last nest incremented: 3
Indices: 4 0 0 1 0 , Last nest incremented: 2
Indices: 4 0 0 1 1 , Last nest incremented: 3
Indices: 4 0 1 0 0 , Last nest incremented: 1
Indices: 4 0 1 0 1 , Last nest incremented: 3
...Jump Second Nest (index 1)...
Indices: 4 0 2 0 0 , Last nest incremented: 1
Indices: 4 0 2 0 1 , Last nest incremented: 3
Indices: 4 0 2 1 0 , Last nest incremented: 2
Indices: 4 0 2 1 1 , Last nest incremented: 3
Indices: 4 1 0 0 0 , Last nest incremented: 0
Indices: 4 1 0 0 1 , Last nest incremented: 3
Indices: 4 1 0 1 0 , Last nest incremented: 2
Indices: 4 1 0 1 1 , Last nest incremented: 3
Indices: 4 1 1 0 0 , Last nest incremented: 1
Indices: 4 1 1 0 1 , Last nest incremented: 3
Indices: 4 1 1 1 0 , Last nest incremented: 2
Indices: 4 1 1 1 1 , Last nest incremented: 3
Indices: 4 1 2 0 0 , Last nest incremented: 1
Indices: 4 1 2 0 1 , Last nest incremented: 3
Indices: 4 1 2 1 0 , Last nest incremented: 2
Indices: 4 1 2 1 1 , Last nest incremented: 3
*/
È possibile utilizzare N chiamate ricorsive a una funzione che contiene un ciclo for. –