public static <V> void reindex(
		final TreeNode<Op<V>> tree,
		final Map<Var<V>, Integer> indexes
	) {
		for (TreeNode<Op<V>> node : tree) {
			final Op<V> op = node.value();
			if (op instanceof Var) {
				node.value(Var.of(op.name(), indexes.get(op)));
			}
		}
	}
Re-indexes the variables of the given operation {@code tree}. If the
operation tree is created from its string representation, the indices
of the variables ({@link Var}), are all set to zero, since it needs the
whole tree for setting the indices correctly.

{@snippet lang="java":
final TreeNode<Op<Double>> tree = TreeNode.parse(
    "add(mul(x,y),sub(y,x))",
    MathOp::toMathOp
);

assert Program.eval(tree, 10.0, 5.0) == 100.0; // wrong result
final Map<Var<Double>, Integer> indexes = new HashMap<>();
indexes.put(Var.of("x"), 0);
indexes.put(Var.of("y"), 1);
Var.reindex(tree, indexes);
assert Program.eval(tree, 10.0, 5.0) == 45.0; // correct result
}
The example above shows a use-case of this method. If you parse a tree
string and convert it to an operation tree, you have to re-index the
variables first. If not, you will get the wrong result when evaluating
the tree. After the re-indexing, you will get the correct result of 45.0.

@since 5.0

@see MathOp#toMathOp(String)
@see BoolOp#toBoolOp(String)
@see Program#eval(Tree, Object[])

@param tree the tree where the variable indices need to be fixed
@param indexes the variable to index mapping
@param <V> the operation value type
jenetics.prog/src/main/java/io/jenetics/prog/op/Var.java