A pascal matrix is a two-dimensional square matrix holding numbers from   Pascal's triangle,   also known as   binomial coefficients   and which can be shown as   nCr.

Shown below are truncated   5-by-5   matrices   M[i, j]   for   i,j   in range   0..4. 


A Pascal upper-triangular matrix that is populated with   jCi:

[[1, 1, 1, 1, 1],
 [0, 1, 2, 3, 4],
 [0, 0, 1, 3, 6],
 [0, 0, 0, 1, 4],
 [0, 0, 0, 0, 1]]

A Pascal lower-triangular matrix that is populated with   iCj   (the transpose of the upper-triangular matrix):

[[1, 0, 0, 0, 0],
 [1, 1, 0, 0, 0],
 [1, 2, 1, 0, 0],
 [1, 3, 3, 1, 0],
 [1, 4, 6, 4, 1]]

A Pascal symmetric matrix that is populated with   i+jCi:

[[1, 1, 1, 1, 1],
 [1, 2, 3, 4, 5],
 [1, 3, 6, 10, 15],
 [1, 4, 10, 20, 35],
 [1, 5, 15, 35, 70]]



Task

Write functions capable of generating each of the three forms of   n-by-n   matrices.

Use those functions to display upper, lower, and symmetric Pascal   5-by-5   matrices on this page.

The output should distinguish between different matrices and the rows of each matrix   (no showing a list of 25 numbers assuming the reader should split it into rows).



Note
 
The   Cholesky decomposition   of a Pascal symmetric matrix is the Pascal lower-triangle matrix of the same size.




program Pascal_matrix(Output);
 
const N = 5;
 
type NxN_Matrix = array[0..N,0..N] of integer;
 
var PM,PX : NxN_Matrix;
 
function Pascal_sym(x : integer; p : NxN_Matrix) : NxN_Matrix;
var I,J : integer;
  begin
    for I := 1 to x do
    begin
      for J := 1 to x do p[I,J] := p[I-1,J]+p[I,J-1]
    end;
    Pascal_sym := p;
  end;
 
function Pascal_upp(x : integer; p : NxN_Matrix) : NxN_Matrix;
var I,J : integer;
  begin
    for I := 1 to x do
    begin
      for J := 1 to x do p[I,J] := p[I-1,J-1]+p[I,J-1]
    end;
    Pascal_upp := p
  end;
 
function Pascal_low(x : integer; p : NxN_Matrix) : NxN_Matrix;
var p1,p2 : NxN_Matrix;
  I,J : integer;
  begin
    p1 := Pascal_upp(x,p);
    p2 := p1;
    for I := 1 to x do
    begin
      for J := 1 to x do p1[J,I] := p2[I,J]
    end;
    Pascal_low := p1
  end;
 
procedure PrintMatrix(titel : ansistring; x : integer; p : NxN_Matrix);
var I,J : integer;
  begin
    writeln(titel);
    for I := 1 to x do
    begin
      for J := 1 to x do write(p[I,J]:5);
      writeln('');
    end;
  end;
 
begin
  PX[0,0] := 0;
  PM[0,0] := 1;
  PM := Pascal_upp(N, PM);
  PrintMatrix('Upper:', N, PM);
  writeln('');
  PM := PX;
  PM[0,0] := 1;
  PM := Pascal_low(N, PM);
  PrintMatrix('Lower:', N, PM);
  writeln('');
  PM := PX;
  PM[1,0] := 1;
  PM := Pascal_sym(N, PM);
  PrintMatrix('Symmetric', N, PM);
  writeln('');
  readln;
end.