// Do actually the computation set<Assignment> SPGParser::computeReductible(int i, int j) { set<Assignment> as; // Base case if(i == j && isType(i)) { if(isUnit(i)) as.insert(Assignment::singleton(headType[i])); return as; } if(j == i+1) { if(isType(i) && isType(j) && gcon(i,j)) { as.insert(Assignment::singleton(headType[i])); // we could add j but headType[i] == headType[j] so it's no use } return as; } if(isType(i) && isType(j) && isStar(i+1) && isStar(j-1) && widx[j] == widx[i]+1 && gcon(i,j)) { Assignment a = Assignment::singleton(headType[i]); a.insert(headType[j]); as.insert(a); return as; } if(isType(i) && isType(j)) { // A1a for(int k = i+1; k < j-1; k++) if(isType(k) && reductible(i,k) && reductible(k+1,j)) as = as + product(assignments[i][k], assignments[k+1][j]); // A1b for(int k = i+1; k < j-1; k++) if(isRB(k) && isLB(k+1) && reductible(i,k) && reductible(k+1,j)) as = as + product(assignments[i][k], assignments[k+1][j]); // A2 if(gcon(i,j) && reductible(i+1,j-1)) { set<Assignment> a = assignments[i+1][j-1]; Assignment rhs; rhs.insert(headType[i]); rhs.insert(headType[j]); set<Assignment> b; b.insert(rhs); as = as + product(a, b); } } // A3a if(isLB(i) && isType(j)) { for(int k = i+1; k < j && widx[k] == widx[i]; k++) if(isStar(k) && reductible(k+1, j)) as = as + assignments[k+1][j]; } // A3b if(isRB(j) && isType(i)) { for(int k = j-1; k > i && widx[k] == widx[j]; k--) if(isStar(k) && reductible(i,k-1)) as = as + assignments[i][k-1]; } // A4a if(isType(i) && isType(j) && isStar(i+1) && gcon(i,j) && widx[i] != widx[j]) { for(int k = i+1; k < j && widx[k] == widx[i]; k++) if(isLB(k+1) && reductible(k+1,j-1)) as = as + assignments[k+1][j-1]; } // A4b if(isType(i) && isType(j) && isStar(j-1) && gcon(i,j) && widx[i] != widx[j]) { for(int k = j-1; k > i && widx[k] == widx[j]; k--) if(isRB(k-1) && reductible(i+1,k-1)) as = as + assignments[i+1][k-1]; } // A4c if(isType(i) && isType(j) && isStar(i+1) && isStar(j-1) && 1 + widx[i] < widx[j] && gcon(i,j)) { int k1, k2; for(k1 = i+1; k1 < j && !isRB(k1); k1++); for(k2 = j-1; k2 > i && !isLB(k2); k2--); if(reductible(k1,k2)) as = as + assignments[k1][k2]; } // A5 if(isLB(i) && isRB(j)) { float totalProb = 0; for(int k1 = i+1; k1 < j && !isRB(k1); k1++) { if(isType(k1) && isStar(k1-1)) { for(int k2 = j-2; k2 > i && !isLB(k2); k2--) { if(isType(k2) && isStar(k2+1) && reductible(k1,k2)) as = as + assignments[k1][k2]; } } } } return as; }
//! Create a singleton Assignment Assignment::singleton(int n) { Assignment a; a.insert(n); return a; }