Logo

SQL Server TMCROSS Function

Updated 2023-10-17 16:01:28.697000

Description

Use the table-valued function TMCROSS to calculate the matrix cross-product of 2 matrices. When only one matrix is passed into the function the result is A * A', otherwise the result is A * B'.

Syntax

SELECT * FROM [wct].[TMCROSS](
  <@A, nvarchar(max),>
 ,<@B, nvarchar(max),>
 ,<@Is3N, bit,>)

Arguments

@A

the SELECT statement which returns the resultant table containing the A matrix.

@B

the SELECT statement which returns the resultant table containing the B matrix.

@Is3N

a bit value identifying the form for the resultant table returned by @A and @B. Enter 'True' for a resultant table in 3rd normal form. Enter 'False' for a de-normalized table in 'spreadsheet' form.

Return Type

table

colNamecolDatatypecolDesc
RowNumintThe zero-based row index for the matrix
ColNumintThe zero-based column index for the matrix
ItemValuefloatThe value at RowNum, ColNum

Remarks

If @Is3N is NULL then @Is3N = 'False'.

If @Is3N is'True' then the result table should be returned as row, column, and value.

If the resultant table contains NULL, then NULL will be returned.

The function returns an error if the array contains a non-numeric value.

If @B IS NULL then the function computes A * A'.

If @B IS NOT NULL then the number of columns in @A must equal to the number of columns in @B.

If @B IS NULL then the function returns an m-by-m matrix where m is the number of rows in @A.

If @B IS NOT NULL then the function returns an m-by-p matrix where m is the number of rows in @A and p is the number of rows in @B.

Examples

In this example we calculate A * A' using a matrix in spreadsheet format.

SELECT *
FROM wct.TMCROSS(
                    'SELECT
          *
       FROM (VALUES
          (1,1,1,1),
          (1,2,4,8),
          (1,3,9,27),
          (1,4,16,64),
          (1,5,25,125)
          )n(x1,x2,x3,x4)',
                    NULL,
                    'False'
                );

This produces the following result.

RowNumColNumItemValue
004
0115
0240
0385
04156
1015
1185
12259
13585
141111
2040
21259
22820
231885
243616
3085
31585
321885
334369
348421
40156
411111
423616
438421
4416276

In this example, we supply the same matrix, except that it is now in 3 rd normal form.

SELECT *
FROM wct.TMCROSS(
                    '
   SELECT
       r.n,
       c.n,
       POWER(r.n,c.n)
   FROM (VALUES (1),(2),(3),(4),(5))r(n)
   CROSS APPLY (VALUES (0),(1),(2),(3))c(n)
   ORDER BY 1,2',
                    NULL,
                    'True'
                );

This produces the following results.

RowNumColNumItemValue
004
0115
0240
0385
04156
1015
1185
12259
13585
141111
2040
21259
22820
231885
243616
3085
31585
321885
334369
348421
40156
411111
423616
438421
4416276

In this example we supply both an A and a B matrix in spreadsheet form and calculate A * B'. We will do this by creating 2 temporary tables for the A and the B matrix and then selecting from the tables in the TMCROSS function.

--Create matrix A
SELECT r.n as rn,
       POWER(r.n, 0) as x0,
       POWER(r.n, 1) as x1,
       POWER(r.n, 2) as x2,
       POWER(r.n, 3) as x3
INTO #A
FROM
(
    VALUES
        (1),
        (2),
        (3),
        (4),
        (5)
) r (n);
--Create matrix B
SELECT r.n as rn,
       1 / POWER(cast(r.n as float), 0) as x0,
       1 / POWER(cast(r.n as float), 1) as x1,
       1 / POWER(cast(r.n as float), 2) as x2,
       1 / POWER(cast(r.n as float), 3) as x3
INTO #B
FROM
(
    VALUES
        (1),
        (2),
        (3)
) r (n);
--A * B'
SELECT *
FROM wct.TMCROSS('SELECT x0,x1,x2,x3 FROM #A order by rn', 'SELECT x0,x1,x2,x3 
          FROM #B order by rn', 'False');

This produces the following result.

RowNumColNumItemValue
004
011.875
021.48148148148148
1015
114
122.40740740740741
2040
218.125
224
3085
3115
326.48148148148148
40156
4125.375
4210.0740740740741

Performing the same calculation as in the previous example, except that this time the data in matrices A and B are in 3 rd normal form.

--Create the A Matrix
SELECT r.n as rowno,
       c.n as colno,
       POWER(r.n, c.n) as x
INTO #A
FROM
(
    VALUES
        (1),
        (2),
        (3),
        (4),
        (5)
) r (n)
    CROSS APPLY
(
    VALUES
        (0),
        (1),
        (2),
        (3)
) c (n);
--Create the B Matrix
SELECT r.n as rowno,
       c.n as colno,
       1 / POWER(cast(r.n as float), c.n) as x
INTO #B
FROM
(
    VALUES
        (1),
        (2),
        (3)
) r (n)
    CROSS APPLY
(
    VALUES
        (0),
        (1),
        (2),
        (3)
) c (n);
--A' * B
SELECT *
FROM wct.TMCROSS('SELECT * FROM #A order by 1,2', 'SELECT * FROM #B order by 1,2',
          'True');

This produces the following result.

RowNumColNumItemValue
004
011.875
021.48148148148148
1015
114
122.40740740740741
2040
218.125
224
3085
3115
326.48148148148148
40156
4125.375
4210.0740740740741

See Also

MATMULT - matrix multiplication for string representations of matrices

MCROSS - table-valued function to calculate A' * A or A' * B

MMULT_Q - Calculate the matrix product of two arrays.

CROSSPROD - scalar function to calculate A' * A or A' * B

TCROSSPROD - scalar function to calculate A * A' or A * B'

TRANSPOSE - scalar function to convert A to A'