11 #ifndef MI_MATH_MATRIX_H
 
   12 #define MI_MATH_MATRIX_H
 
   88 template <
typename T, Size ROW, Size COL>
 
  278 template <
typename T, 
class Matrix, 
bool specialized>
 
  279 struct Matrix_struct_get_base_pointer
 
  282     static inline const T* get_base_ptr( 
const Matrix& m) { 
return m.elements; }
 
  287 template <
typename T, 
class Matrix>
 
  288 struct Matrix_struct_get_base_pointer<T,Matrix,true>
 
  290     static inline T*       get_base_ptr( Matrix& m)       { 
return &m.xx; }
 
  291     static inline const T* get_base_ptr( 
const Matrix& m) { 
return &m.xx; }
 
  296 template <
typename T, Size ROW, Size COL>
 
  299     return Matrix_struct_get_base_pointer<T,Matrix_struct<T,ROW,COL>,
 
  300                (ROW<=4 && COL<=4)>::get_base_ptr( mat);
 
  304 template <
typename T, Size ROW, Size COL>
 
  307     return Matrix_struct_get_base_pointer<T,Matrix_struct<T,ROW,COL>,
 
  308                (ROW<=4 && COL<=4)>::get_base_ptr( mat);
 
  364 template <
typename T, Size ROW, Size COL>
 
  439         for( 
Size i(0u); i < ROW * COL; ++i)
 
  450         const Size MIN_DIM = (ROW < COL) ? ROW : COL;
 
  451         for( 
Size k(0u); k < MIN_DIM; ++k)
 
  452             begin()[k * COL + k] = diag;
 
  468     template <
typename Iterator>
 
  471         for( 
Size i(0u); i < 
SIZE; ++i, ++p)
 
  487     template <
typename T2>
 
  491             begin()[i] = array[i];
 
  496     template <
typename T2>
 
  508         for( 
Size i(0u); i < ROW; ++i)
 
  509             for( 
Size j(0u); j < COL; ++j)
 
  510                 begin()[i * COL + j] = other.
begin()[j * ROW + i];
 
  516     template <
typename T2>
 
  521         for( 
Size i(0u); i < ROW; ++i)
 
  522             for( 
Size j(0u); j < COL; ++j)
 
  523                 begin()[i * COL + j] = T(other.
begin()[j * ROW + i]);
 
  612     inline Matrix( T m0, T m1, T m2, T m3, T m4, T m5)
 
  622     inline Matrix( T m0, T m1, T m2, T m3, T m4, T m5, T m6, T m7)
 
  632     inline Matrix( T m0, T m1, T m2, T m3, T m4, T m5, T m6, T m7, T m8)
 
  644         T  m0, T  m1, T  m2, T  m3,
 
  645         T  m4, T  m5, T  m6, T  m7,
 
  646         T  m8, T  m9, T m10, T m11)
 
  658         T  m0, T  m1, T  m2, T  m3,
 
  659         T  m4, T  m5, T  m6, T  m7,
 
  660         T  m8, T  m9, T m10, T m11,
 
  661         T m12, T m13, T m14, T m15)
 
  684         return begin()[row * COL + col];
 
  694         return begin()[row * COL + col];
 
  713         return begin()[row * COL + col];
 
  734         begin()[row * COL + col] = value;
 
  743         return this->xx * this->yy * this->zz
 
  744              + this->xy * this->yz * this->zx
 
  745              + this->xz * this->yx * this->zy
 
  746              - this->xx * this->zy * this->yz
 
  747              - this->xy * this->zz * this->yx
 
  748              - this->xz * this->zx * this->yy;
 
  764         for( 
Size i=0; i < ROW-1; ++i) {
 
  765             for( 
Size j=i+1; j < COL; ++j) {
 
  788         this->wx += T( vector.x);
 
  789         this->wy += T( vector.y);
 
  790         this->wz += T( vector.z);
 
  798         this->wx += T( vector.x);
 
  799         this->wy += T( vector.y);
 
  800         this->wz += T( vector.z);
 
  818         this->wx = T( vector.x);
 
  819         this->wy = T( vector.y);
 
  820         this->wz = T( vector.z);
 
  828         this->wx = T( vector.x);
 
  829         this->wy = T( vector.y);
 
  830         this->wz = T( vector.z);
 
  837     inline void rotate( T xangle, T yangle, T zangle)
 
  851         tmp.
set_rotation( T( angles.x), T( angles.y), T( angles.z));
 
  862         tmp.
set_rotation( T( angles.x), T( angles.y), T( angles.z));
 
  871     inline void set_rotation( T x_angle, T y_angle, T z_angle);
 
  880         set_rotation( T( angles.x), T( angles.y), T( angles.z));
 
  890         set_rotation( T( angles.x), T( angles.y), T( angles.z));
 
  928 #ifdef MI_NEURAYLIB_DEPRECATED_5_0
 
  934     inline void rotateaxis( 
const Vector<Float64,3>& axis, 
Float64 angle)
 
  939     inline void multiply( 
const Matrix<Float32,4,4>& matrix);
 
  941     inline void multiply( 
const Matrix<Float64,4,4>& matrix);
 
  943     inline Vector<Float32,3> 
transform( 
const Vector<Float32,3> vector) 
const;
 
  945     inline Vector<Float64,3> 
transform( 
const Vector<Float64,3> vector) 
const;
 
  947     inline Vector<Float32,3> transform33( 
const Vector<Float32,3> vector) 
const;
 
  949     inline Vector<Float64,3> transform33( 
const Vector<Float64,3> vector) 
const;
 
  951     inline Vector<Float32,3> transform33t( 
const Vector<Float32,3> vector) 
const;
 
  953     inline Vector<Float64,3> transform33t( 
const Vector<Float64,3> vector) 
const;
 
  954 #endif // MI_NEURAYLIB_DEPRECATED_5_0
 
  961 template <
typename T, Size ROW, Size COL>
 
  970 template <
typename T, Size ROW, Size COL>
 
  981 template <
typename T, Size ROW, Size COL>
 
  992 template <
typename T, Size ROW, Size COL>
 
 1003 template <
typename T, Size ROW, Size COL>
 
 1014 template <
typename T, Size ROW, Size COL>
 
 1025 template <
typename T, Size ROW, Size COL>
 
 1026 Matrix<T,ROW,COL>& 
operator+=( Matrix<T,ROW,COL>& lhs, 
const Matrix<T,ROW,COL>& rhs);
 
 1029 template <
typename T, Size ROW, Size COL>
 
 1030 Matrix<T,ROW,COL>& 
operator-=( Matrix<T,ROW,COL>& lhs, 
const Matrix<T,ROW,COL>& rhs);
 
 1033 template <
typename T, Size ROW, Size COL>
 
 1044 template <
typename T, Size ROW, Size COL>
 
 1055 template <
typename T, Size ROW, Size COL>
 
 1060     for( 
Size i(0u); i < (ROW*COL); ++i)
 
 1071 template <
typename T, Size ROW, Size COL>
 
 1079     for( 
Size rrow = 0; rrow < ROW; ++rrow) {
 
 1080         for( 
Size rcol = 0; rcol < COL; ++rcol) {
 
 1081             lhs( rrow, rcol) = T(0);
 
 1082             for( 
Size k = 0; k < COL; ++k)
 
 1083                 lhs( rrow, rcol) += old( rrow, k) * rhs( k, rcol);
 
 1094 template <
typename T, Size ROW1, Size COL1, Size ROW2, Size COL2>
 
 1103     for( 
Size rrow = 0; rrow < ROW1; ++rrow) {
 
 1104         for( 
Size rcol = 0; rcol < COL2; ++rcol) {
 
 1105             result( rrow, rcol) = T(0);
 
 1106             for( 
Size k = 0; k < COL1; ++k)
 
 1107                 result( rrow, rcol) += lhs( rrow, k) * rhs( k, rcol);
 
 1120 template <
typename T, Size ROW, Size COL, Size DIM>
 
 1127     for( 
Size row = 0; row < ROW; ++row) {
 
 1129         for( 
Size col = 0; col < COL; ++col)
 
 1130             result[row] += mat( row, col) * vec[col];
 
 1141 template <Size DIM, 
typename T, Size ROW, Size COL>
 
 1148     for( 
Size col = 0; col < COL; ++col) {
 
 1150         for( 
Size row = 0; row < ROW; ++row)
 
 1151             result[col] += mat( row, col) * vec[row];
 
 1158 template <
typename T, Size ROW, Size COL>
 
 1161     for( 
Size i=0; i < (ROW*COL); ++i)
 
 1162         mat.
begin()[i] *= factor;
 
 1167 template <
typename T, Size ROW, Size COL>
 
 1176 template <
typename T, Size ROW, Size COL>
 
 1190 template <Size NEW_ROW, Size NEW_COL, 
typename T, Size ROW, Size COL>
 
 1197     for( 
Size i=0; i < NEW_ROW; ++i)
 
 1198         for( 
Size j=0; j < NEW_COL; ++j)
 
 1199             result( i, j) = mat( i, j);
 
 1206 template <
typename T, Size ROW, Size COL>
 
 1211     for( 
Size i=0; i < ROW; ++i)
 
 1212         for( 
Size j=0; j < COL; ++j)
 
 1213             result( j, i) = mat( i, j);
 
 1222 template <
typename T, 
typename U>
 
 1227     const T w = T(mat.xw * point + mat.ww);
 
 1228     if( w == T(0) || w == T(1))
 
 1229         return U(mat.xx * point + mat.wx);
 
 1231         return U((mat.xx * point + mat.wx) / w);
 
 1239 template <
typename T, 
typename U>
 
 1244     T w = T(mat.xw * point.x + mat.yw * point.y + mat.ww);
 
 1245     if( w == T(0) || w == T(1))
 
 1247             U(mat.xx * point.x + mat.yx * point.y + mat.wx),
 
 1248             U(mat.xy * point.x + mat.yy * point.y + mat.wy));
 
 1252             U((mat.xx * point.x + mat.yx * point.y + mat.wx) * w),
 
 1253             U((mat.xy * point.x + mat.yy * point.y + mat.wy) * w));
 
 1262 template <
typename T, 
typename U>
 
 1267     T w = T(mat.xw * point.x + mat.yw * point.y + mat.zw * point.z + mat.ww);
 
 1268     if( w == T(0) || w == T(1)) 
 
 1270             U(mat.xx * point.x + mat.yx * point.y + mat.zx * point.z + mat.wx),
 
 1271             U(mat.xy * point.x + mat.yy * point.y + mat.zy * point.z + mat.wy),
 
 1272             U(mat.xz * point.x + mat.yz * point.y + mat.zz * point.z + mat.wz));
 
 1276             U((mat.xx * point.x + mat.yx * point.y + mat.zx * point.z + mat.wx) * w),
 
 1277             U((mat.xy * point.x + mat.yy * point.y + mat.zy * point.z + mat.wy) * w),
 
 1278             U((mat.xz * point.x + mat.yz * point.y + mat.zz * point.z + mat.wz) * w));
 
 1287 template <
typename T, 
typename U>
 
 1293         U(mat.xx * point.x + mat.yx * point.y + mat.zx * point.z + mat.wx * point.w),
 
 1294         U(mat.xy * point.x + mat.yy * point.y + mat.zy * point.z + mat.wy * point.w),
 
 1295         U(mat.xz * point.x + mat.yz * point.y + mat.zz * point.z + mat.wz * point.w),
 
 1296         U(mat.xw * point.x + mat.yw * point.y + mat.zw * point.z + mat.ww * point.w));
 
 1304 template <
typename T, 
typename U>
 
 1309     return U(mat.xx * vector);
 
 1317 template <
typename T, 
typename U>
 
 1323         U(mat.xx * vector.x + mat.yx * vector.y),
 
 1324         U(mat.xy * vector.x + mat.yy * vector.y));
 
 1332 template <
typename T, 
typename U>
 
 1338         U(mat.xx * vector.x + mat.yx * vector.y + mat.zx * vector.z),
 
 1339         U(mat.xy * vector.x + mat.yy * vector.y + mat.zy * vector.z),
 
 1340         U(mat.xz * vector.x + mat.yz * vector.y + mat.zz * vector.z));
 
 1354 template <
typename T, 
typename U>
 
 1360         U(inv_mat.xx * normal.x + inv_mat.xy * normal.y + inv_mat.xz * normal.z),
 
 1361         U(inv_mat.yx * normal.x + inv_mat.yy * normal.y + inv_mat.yz * normal.z),
 
 1362         U(inv_mat.zx * normal.x + inv_mat.zy * normal.y + inv_mat.zz * normal.z));
 
 1378 template <
typename T, 
typename U>
 
 1384                            mat.yx, mat.yy, mat.yz,
 
 1385                            mat.zx, mat.zy, mat.zz);
 
 1386     bool inverted = sub_mat.
invert();
 
 1390         U(sub_mat.xx * normal.x + sub_mat.xy * normal.y + sub_mat.xz * normal.z),
 
 1391         U(sub_mat.yx * normal.x + sub_mat.yy * normal.y + sub_mat.yz * normal.z),
 
 1392         U(sub_mat.zx * normal.x + sub_mat.zy * normal.y + sub_mat.zz * normal.z));
 
 1398 template <
typename T, Size ROW, Size COL>
 
 1403     for( 
Size i=0; i < ROW*COL; ++i)
 
 1408 template <
typename T, Size ROW, Size COL>
 
 1413     for( 
Size i=0; i < ROW*COL; ++i)
 
 1418 #ifndef MI_FOR_DOXYGEN_ONLY
 
 1420 template <
typename T, Size ROW, Size COL>
 
 1427     const T min_angle = T(0.00024f);
 
 1429     if( 
abs( xangle) > min_angle) {
 
 1436     if( 
abs( yangle) > min_angle) {
 
 1443     if( 
abs(zangle) > min_angle) {
 
 1450     this->xx = tcy * tcz;
 
 1451     this->xy = tcy * tsz;
 
 1455     this->yx = tmp * tcz - tcx * tsz;
 
 1456     this->yy = tmp * tsz + tcx * tcz;
 
 1457     this->yz = tsx * tcy;
 
 1460     this->zx = tmp * tcz + tsx * tsz;
 
 1461     this->zy = tmp * tsz - tsx * tcz;
 
 1462     this->zz = tcx * tcy;
 
 1465 template <
typename T, Size ROW, Size COL>
 
 1469     Vector<T,3> axis( axis_v);
 
 1470     const T min_angle = T(0.00024f);
 
 1472     if( 
abs( T(angle)) < min_angle) {
 
 1473         T xa = axis.x * T(angle);
 
 1474         T ya = axis.y * T(angle);
 
 1475         T za = axis.z * T(angle);
 
 1492         T s = 
sin( T(angle));
 
 1493         T c = 
cos( T(angle));
 
 1497         tmp = t * T(axis.x);
 
 1498         this->xx  = tmp * T(axis.x) + c;
 
 1499         this->xy  = tmp * T(axis.y) + s * T(axis.z);
 
 1500         this->xz  = tmp * T(axis.z) - s * T(axis.y);
 
 1503         tmp = t * T(axis.y);
 
 1504         this->yx  = tmp * T(axis.x) - s * T(axis.z);
 
 1505         this->yy  = tmp * T(axis.y) + c;
 
 1506         this->yz  = tmp * T(axis.z) + s * T(axis.x);
 
 1509         tmp = t * T(axis.z);
 
 1510         this->zx  = tmp * T(axis.x) + s * T(axis.y);
 
 1511         this->zy  = tmp * T(axis.y) - s * T(axis.x);
 
 1512         this->zz  = tmp * T(axis.z) + c;
 
 1515     this->wx = this->wy = this->wz = T(0);
 
 1519 template <
typename T, Size ROW, Size COL>
 
 1523     Vector<T,3> axis( axis_v);
 
 1524     const T min_angle = T(0.00024f);
 
 1526     if( 
abs(T(angle)) < min_angle) {
 
 1527         T xa = axis.x * T(angle);
 
 1528         T ya = axis.y * T(angle);
 
 1529         T za = axis.z * T(angle);
 
 1546         T s = 
sin( T(angle));
 
 1547         T c = 
cos( T(angle));
 
 1551         tmp = t * T(axis.x);
 
 1552         this->xx  = tmp * T(axis.x) + c;
 
 1553         this->xy  = tmp * T(axis.y) + s * T(axis.z);
 
 1554         this->xz  = tmp * T(axis.z) - s * T(axis.y);
 
 1557         tmp = t * T(axis.y);
 
 1558         this->yx  = tmp * T(axis.x) - s * T(axis.z);
 
 1559         this->yy  = tmp * T(axis.y) + c;
 
 1560         this->yz  = tmp * T(axis.z) + s * T(axis.x);
 
 1563         tmp = t * T(axis.z);
 
 1564         this->zx  = tmp * T(axis.x) + s * T(axis.y);
 
 1565         this->zy  = tmp * T(axis.y) - s * T(axis.x);
 
 1566         this->zz  = tmp * T(axis.z) + c;
 
 1569     this->wx = this->wy = this->wz = T(0);
 
 1573 template <
typename T, Size ROW, Size COL>
 
 1575     const Vector<Float32,3>& position,
 
 1576     const Vector<Float32,3>& target,
 
 1577     const Vector<Float32,3>& up)
 
 1580     Vector<Float32,3> xaxis, yaxis, zaxis;
 
 1583     zaxis = position - target;
 
 1587     xaxis = 
cross( up, zaxis);
 
 1591     yaxis = 
cross( zaxis, xaxis);
 
 1596         T(xaxis.x), T(yaxis.x), T(zaxis.x), T(0),
 
 1597         T(xaxis.y), T(yaxis.y), T(zaxis.y), T(0),
 
 1598         T(xaxis.z), T(yaxis.z), T(zaxis.z), T(0),
 
 1599         T(0),       T(0),       T(0),       T(1));
 
 1602     Matrix<T,4,4> trans(
 
 1603         T(1),      T(0),      T(0),      T(0),
 
 1604         T(0),      T(1),      T(0),      T(0),
 
 1605         T(0),      T(0),      T(1),      T(0),
 
 1606         T(-position.x), T(-position.y), T(-position.z), T(1));
 
 1608     *
this = trans * rot;
 
 1611 template <
typename T, Size ROW, Size COL>
 
 1613     const Vector<Float64,3>& position,
 
 1614     const Vector<Float64,3>& target,
 
 1615     const Vector<Float64,3>& up)
 
 1618     Vector<Float64,3> xaxis, yaxis, zaxis;
 
 1621     zaxis = position - target;
 
 1625     xaxis = 
cross( up, zaxis);
 
 1629     yaxis = 
cross( zaxis, xaxis);
 
 1634         T(xaxis.x), T(yaxis.x), T(zaxis.x), T(0),
 
 1635         T(xaxis.y), T(yaxis.y), T(zaxis.y), T(0),
 
 1636         T(xaxis.z), T(yaxis.z), T(zaxis.z), T(0),
 
 1637         T(0),       T(0),       T(0),       T(1));
 
 1640     Matrix<T,4,4> trans(
 
 1641         T(1),      T(0),      T(0),      T(0),
 
 1642         T(0),      T(1),      T(0),      T(0),
 
 1643         T(0),      T(0),      T(1),      T(0),
 
 1644         T(-position.x), T(-position.y), T(-position.z), T(1));
 
 1646     *
this = trans * rot;
 
 1653 template <
class T, Size ROW, Size COL>
 
 1654 class Matrix_inverter
 
 1657     typedef math::Matrix<T,ROW,COL> Matrix;
 
 1662     static inline bool invert( Matrix& ) { 
return false; }
 
 1666 template <
class T, Size DIM>
 
 1667 class Matrix_inverter<T,DIM,DIM>
 
 1670     typedef math::Matrix<T,DIM,DIM> Matrix;
 
 1671     typedef math::Vector<T,DIM>     Vector;
 
 1672     typedef math::Vector<Size,DIM>  Index_vector;
 
 1678     static bool lu_decomposition(
 
 1680         Index_vector& indx);      
 
 1684     static void lu_backsubstitution(
 
 1686         const Index_vector& indx, 
 
 1689     static bool invert( Matrix& mat);
 
 1692 template <
class T, Size DIM>
 
 1693 bool  Matrix_inverter<T,DIM,DIM>::lu_decomposition(
 
 1699     for( 
Size i = 0; i < DIM; i++) {    
 
 1701         for( 
Size j = 0; j < DIM; j++) {
 
 1702             T temp = 
abs(lu.get(i,j));
 
 1714     for( 
Size j = 0; j < DIM; j++) {
 
 1715         for( 
Size i = 0; i < j; i++) {
 
 1716             T sum = lu.get(i,j);
 
 1717             for( 
Size k = 0; k < i; k++)
 
 1718                 sum -= lu.get(i,k) * lu.get(k,j);
 
 1722         for( 
Size i = j; i < DIM; i++) {
 
 1723             T sum = lu.get(i,j);
 
 1724             for( 
Size k = 0; k < j; k++)
 
 1725                 sum -= lu.get(i,k) * lu.get(k,j);
 
 1727             T dum = vv[i] * 
abs(sum);
 
 1734             for( 
Size k = 0; k < DIM; k++) {
 
 1735                 T dum = lu.get(imax,k);
 
 1736                 lu.set(imax, k, lu.get(j,k));
 
 1742         if( lu.get(j,j) == 0)
 
 1745             T dum = T(1) / lu.get(j,j);
 
 1746             for( 
Size i = j + 1; i < DIM; i++)
 
 1747                 lu.set(i, j, lu.get(i,j) * dum);
 
 1753 template <
class T, Size DIM>
 
 1754 void Matrix_inverter<T,DIM,DIM>::lu_backsubstitution(
 
 1756     const Index_vector& indx,
 
 1761     for( 
Size i = 0; i < DIM; i++) {
 
 1766             for( 
Size j = ii; j < i; j++) {
 
 1767                 sum -= lu.get(i,j) * b[j];
 
 1776     for( 
Size i2 = DIM; i2 > 0;) {      
 
 1779         for( 
Size j = i2+1; j < DIM; j++)
 
 1780             sum -= lu.get(i2,j) * b[j];
 
 1781         b[i2] = sum / lu.get(i2,i2);    
 
 1785 template <
class T, Size DIM>
 
 1786 bool  Matrix_inverter<T,DIM,DIM>::invert( Matrix& mat)
 
 1792     if( !lu_decomposition(lu, indx))
 
 1796     for( 
Size j = 0; j < DIM; ++j) {
 
 1799         lu_backsubstitution( lu, indx, col);
 
 1800         for( 
Size i = 0; i < DIM; ++i) {
 
 1801             mat.set( i, j, col[i]);
 
 1809 class Matrix_inverter<T,1,1>
 
 1812     typedef math::Matrix<T,1,1>     Matrix;
 
 1814     static inline bool invert( Matrix& mat)
 
 1816         T s = mat.get( 0, 0);
 
 1819         mat.set( 0, 0, T(1) / s);
 
 1826 class Matrix_inverter<T,2,2>
 
 1829     typedef math::Matrix<T,2,2>        Matrix;
 
 1831     static inline bool invert( Matrix& mat)
 
 1833         T a = mat.get( 0, 0);
 
 1834         T b = mat.get( 0, 1);
 
 1835         T c = mat.get( 1, 0);
 
 1836         T d = mat.get( 1, 1);
 
 1840         T rdet = T(1) / det;
 
 1841         mat.set( 0, 0, d * rdet);
 
 1842         mat.set( 0, 1,-b * rdet);
 
 1843         mat.set( 1, 0,-c * rdet);
 
 1844         mat.set( 1, 1, a * rdet);
 
 1849 template <
typename T, Size ROW, Size COL>
 
 1852     return Matrix_inverter<T,ROW,COL>::invert( *
this);
 
 1860 template <
typename T>
 
 1863     const Matrix<T,4,4>& rhs)
 
 1865     Matrix<T,4,4> old( lhs);
 
 1867     lhs.xx = old.xx * rhs.xx + old.xy * rhs.yx + old.xz * rhs.zx + old.xw * rhs.wx;
 
 1868     lhs.xy = old.xx * rhs.xy + old.xy * rhs.yy + old.xz * rhs.zy + old.xw * rhs.wy;
 
 1869     lhs.xz = old.xx * rhs.xz + old.xy * rhs.yz + old.xz * rhs.zz + old.xw * rhs.wz;
 
 1870     lhs.xw = old.xx * rhs.xw + old.xy * rhs.yw + old.xz * rhs.zw + old.xw * rhs.ww;
 
 1872     lhs.yx = old.yx * rhs.xx + old.yy * rhs.yx + old.yz * rhs.zx + old.yw * rhs.wx;
 
 1873     lhs.yy = old.yx * rhs.xy + old.yy * rhs.yy + old.yz * rhs.zy + old.yw * rhs.wy;
 
 1874     lhs.yz = old.yx * rhs.xz + old.yy * rhs.yz + old.yz * rhs.zz + old.yw * rhs.wz;
 
 1875     lhs.yw = old.yx * rhs.xw + old.yy * rhs.yw + old.yz * rhs.zw + old.yw * rhs.ww;
 
 1877     lhs.zx = old.zx * rhs.xx + old.zy * rhs.yx + old.zz * rhs.zx + old.zw * rhs.wx;
 
 1878     lhs.zy = old.zx * rhs.xy + old.zy * rhs.yy + old.zz * rhs.zy + old.zw * rhs.wy;
 
 1879     lhs.zz = old.zx * rhs.xz + old.zy * rhs.yz + old.zz * rhs.zz + old.zw * rhs.wz;
 
 1880     lhs.zw = old.zx * rhs.xw + old.zy * rhs.yw + old.zz * rhs.zw + old.zw * rhs.ww;
 
 1882     lhs.wx = old.wx * rhs.xx + old.wy * rhs.yx + old.wz * rhs.zx + old.ww * rhs.wx;
 
 1883     lhs.wy = old.wx * rhs.xy + old.wy * rhs.yy + old.wz * rhs.zy + old.ww * rhs.wy;
 
 1884     lhs.wz = old.wx * rhs.xz + old.wy * rhs.yz + old.wz * rhs.zz + old.ww * rhs.wz;
 
 1885     lhs.ww = old.wx * rhs.xw + old.wy * rhs.yw + old.wz * rhs.zw + old.ww * rhs.ww;
 
 1891 template <
typename T>
 
 1893     const Matrix<T,4,4>& lhs,
 
 1894     const Matrix<T,4,4>& rhs)
 
 1896     Matrix<T,4,4> temp( lhs);
 
 1901 #endif // MI_FOR_DOXYGEN_ONLY
 
 1903 #ifdef MI_NEURAYLIB_DEPRECATED_5_0
 
 1905 template <
typename T, Size ROW, Size COL>
 
 1906 inline void Matrix<T,ROW,COL>::multiply( 
const Matrix<Float32,4,4>& matrix)
 
 1909     (*this) *= Matrix<T,ROW,COL> (matrix);
 
 1912 template <
typename T, Size ROW, Size COL>
 
 1913 inline void Matrix<T,ROW,COL>::multiply( 
const Matrix<Float64,4,4>& matrix)
 
 1916     (*this) *= Matrix<T,ROW,COL>( matrix);
 
 1919 template <
typename T, Size ROW, Size COL>
 
 1926 template <
typename T, Size ROW, Size COL>
 
 1933 template <
typename T, Size ROW, Size COL>
 
 1934 inline Vector<Float32,3> Matrix<T,ROW,COL>::transform33( 
const Vector<Float32,3> vector)
 const
 
 1940 template <
typename T, Size ROW, Size COL>
 
 1941 inline Vector<Float64,3> Matrix<T,ROW,COL>::transform33( 
const Vector<Float64,3> vector)
 const
 
 1947 template <
typename T, Size ROW, Size COL>
 
 1948 inline Vector<Float32,3> Matrix<T,ROW,COL>::transform33t( 
const Vector<Float32,3> vector)
 const
 
 1954 template <
typename T, Size ROW, Size COL>
 
 1955 inline Vector<Float64,3> Matrix<T,ROW,COL>::transform33t( 
const Vector<Float64,3> vector)
 const
 
 1961 #endif // MI_NEURAYLIB_DEPRECATED_5_0
 
 1969 #endif // MI_MATH_MATRIX_H