Ответ в теме: Умножение матриц на Prolog

      Комментарии к записи Ответ в теме: Умножение матриц на Prolog отключены
#2051

Для умножения матриц понадобится выделять столбец и строку:

get_row(RowIndex, Matrix, Row):-
nth0(RowIndex, Matrix, Row).

Тут используется встроенная функция nth0 для получения элемента списка.

Функция должна вычислять скалярное произведение строки первой матрицы на столбец второй. Количество строк в первой матрице должно совпадать с количеством столбцов во второй — иначе скалярное произведение соответствующих векторов вычислить невозможно.

Если матрица A[m,n] умножается на матрицу B[n,q] — то в результате будет получена матрица C[m,q], т.е. наша функция должна перемножить m*q векторов. Для этого потребуется вести подсчет векторов (задать начальные значения счетчиков) и знать их количество — это можно сделать во вспомогательной функции:

matrix_multiplication(MatrixA, MatrixB, Multiplication):-
length(MatrixA, RowNumber), 
MatrixB = [RowB|_], length(RowB, ColumnNumber),
matrix_multiplication(MatrixA, MatrixB, 0, 0, RowNumber, ColumnNumber, Multiplication).

Функция умножения матриц должна возвращать пустой список строк если все элементы обработаны — значения будут добавлены на рекурсивном подъеме.
Если закончилась строка матрицы — необходимо перейти к началу следующей строки, прим добавив к результату пустую строчку.
В остальных случаях функция выделяет строку и столбец из исходных матриц, вычисляет их скалярное произведение, остальные элементы матрицы обрабатывает рекурсивно. В результате рекурсивных вычислений будет получена матрица, в первую строку которой необходимо добавить полученное произведение (именно поэтому при переходе на следующую строку к результату добавлялся пустой список).

matrix_multiplication(_MatrixA, _MatrixB, RowIndex, _ColumnIndex, RowNumber, _ColumnNumber, []):-
RowIndex >= RowNumber, !.
matrix_multiplication(MatrixA, MatrixB, RowIndex, ColumnIndex, RowNumber, ColumnNumber, [[]|Multiplication]):-
ColumnIndex >= ColumnNumber, !,
NextRowIndex is RowIndex + 1,
matrix_multiplication(MatrixA, MatrixB, NextRowIndex, 0, RowNumber, ColumnNumber, Multiplication).
matrix_multiplication(MatrixA, MatrixB, RowIndex, ColumnIndex, RowNumber, ColumnNumber, [[Element|RowMul]|TailRowsMul]):-
get_row(RowIndex, MatrixA, Row),
get_column(ColumnIndex, MatrixB, Column),
scalar_multiplication(Row, Column, Element),
NextColumnIndex is ColumnIndex + 1,
matrix_multiplication(MatrixA, MatrixB, RowIndex, NextColumnIndex, RowNumber, ColumnNumber, [RowMul|TailRowsMul]).