public final Program mutate() {
        final int mutationRate = Parameter.MUTATION_RATE.getValue();
        if (Parameter.getNextRandomInt(Parameter.PERCENT) >= mutationRate) {
            return new Program(commands);
        }

        /* mutation! */
        final Vector<Command> newCommands = new Vector<Command>(commands);
        final Command c = Command.getRandom();
        final int length = newCommands.size();

        switch (Parameter.getNextRandomInt(1 + 1 + 1)) {
            case 0: /* delete random instruction */
                newCommands.remove(Parameter.getNextRandomInt(length));
                break;

            case 1: /* insert random instruction */
                newCommands.add(Parameter.getNextRandomInt(length + 1), c);
                break;

            case 2: /* change random instruction */
                newCommands.set(Parameter.getNextRandomInt(length), c);
                break;

            default:
                throw new RuntimeException();
        }

        return new Program(newCommands);
    }