public Tuple<Collection<BasicOperator>, Collection<BasicOperator>> transformOperatorGraph(
final Map<String, BasicOperator> mso,
final BasicOperator rootOperator) {
final Collection<BasicOperator> deleted = new LinkedList<BasicOperator>();
final Collection<BasicOperator> added = new LinkedList<BasicOperator>();
final Join join = (Join) mso.get("join");
final ReplaceVar replaceVar = (ReplaceVar) mso.get("replaceVar");
// Generate a clone
final ReplaceVar originalClone = new ReplaceVar();
originalClone.setSubstitutionsVariableLeft(replaceVar
.getSubstitutionsVariableLeft());
originalClone.setSubstitutionsVariableRight(replaceVar
.getSubstitutionsVariableRight());
final LinkedList<BasicOperator> pres = (LinkedList<BasicOperator>) join
.getPrecedingOperators();
BasicOperator pre;
final LinkedList<Integer> indices = new LinkedList<Integer>();
// Remark the operator-IDs of the precessors
for (int i = 0; i < pres.size(); i++) {
pre = pres.get(i);
indices.add(pre.getOperatorIDTuple(join).getId());
}
ReplaceVar rep;
Projection projectionPre;
for (int i = 0; i < pres.size(); i++) {
pre = pres.get(i);
// Calculate the new ReplaceVar which will be replaced between the
// i-th precessor and the join
rep = getReplaceAfterPre(replaceVar, originalClone, pre, join);
// Calculate projection after precessor and new ReplaceVar
projectionPre = getProjectionAfterReplace(rep, pre);
added.add(rep);
added.add(projectionPre);
pre.setSucceedingOperator(new OperatorIDTuple(rep, 0));
rep.setPrecedingOperator(pre);
rep.setSucceedingOperator(new OperatorIDTuple(projectionPre, 0));
projectionPre.setPrecedingOperator(rep);
projectionPre.setSucceedingOperator(new OperatorIDTuple(join,
indices.get(i)));
join.setPrecedingOperator(projectionPre);
}
rootOperator.deleteParents();
rootOperator.setParents();
rootOperator.detectCycles();