Я немного озадачен тем, как вы могли бы осуществить поиск в ширину, но у меня возникли проблемы с пониманием динамической формулировки, что мне кажется проще:)
Это в значительной степени классическая проблема динамического программирования. При поступлении в любую ячейку solution[y][x]
, кроме первой, имеет не более двух предшественников: option 1
и option 2
. Предположим, что мы знали оптимальное решение для достижения каждого из них, какое преимущество мы бы выбрали? Очевидно, лучший из двух вариантов!
Чуть более формально, если M
содержит заданные значения:
solution[0][0] = M[0][0]
// only one choice along
// the top horizontal and
// left vertical
solution[0][x] =
M[0][x] + solution[0][x - 1]
solution[y][0] =
M[y][0] + solution[y - 1][0]
// two choices otherwise:
// the best of option 1 or 2
solution[y][x] =
M[y][x] + min(
solution[y][x - 1],
solution[y - 1][x]
)
Мы можем видеть, что мы можем создать соответствующую подпрограмму, например, с помощью циклов for
, чтобы посещать ячейки нашей матрицы solution
в порядке «снизу вверх», поскольку значение каждой ячейки зависит от одного или двух предшественников, которые мы бы уже рассчитали.
Код JavaScript:
function show(M){
let str = '';
for (let row of M)
str += JSON.stringify(row) + '\n';
console.log(str);
}
function f(M){
console.log('Input:\n');
show(M);
let solution = new Array();
for (let i=0; i<M.length; i++)
solution.push(new Array(M[0].length).fill(Infinity));
solution[0][0] = M[0][0];
// only one choice along
// the top horizontal and
// left vertical
for (let x=1; x<M[0].length; x++)
solution[0][x] =
M[0][x] + solution[0][x - 1];
for (let y=1; y<M.length; y++)
solution[y][0] =
M[y][0] + solution[y - 1][0];
console.log('Solution borders:\n');
show(solution);
// two choices otherwise:
// the best of option 1 or 2
for (let y=1; y<M.length; y++)
for (let x=1; x<M[0].length; x++)
solution[y][x] =
M[y][x] + Math.min(
solution[y][x - 1],
solution[y - 1][x]
);
console.log('Full solution:\n');
show(solution);
return solution[M.length-1][M[0].length-1];
}
let arr = [];
arr[0] = [0, 7, -7];
arr[1] = [6, 7, -8];
arr[2] = [1, 2, 0];
console.log(f(arr));