()
| 839 | } |
| 840 | |
| 841 | @Override |
| 842 | public Matrix[] qr() |
| 843 | { |
| 844 | int N = cols(), M = rows(); |
| 845 | Matrix[] qr = new Matrix[2]; |
| 846 | |
| 847 | DenseMatrix Q = Matrix.eye(M); |
| 848 | DenseMatrix A; |
| 849 | if(isSquare()) |
| 850 | { |
| 851 | mutableTranspose(); |
| 852 | A = this; |
| 853 | } |
| 854 | else |
| 855 | A = (DenseMatrix) this.transpose(); |
| 856 | int to = cols() > rows() ? M : N; |
| 857 | double[] vk = new double[M]; |
| 858 | for(int k = 0; k < to; k++) |
| 859 | { |
| 860 | double[] A_k = A.matrix[k]; |
| 861 | |
| 862 | double vkNorm = initalVKNormCompute(k, M, vk, A_k); |
| 863 | double beta = vkNorm; |
| 864 | |
| 865 | double vk_k = vk[k] = A_k[k];//force into register, help the JIT! |
| 866 | vkNorm += vk_k*vk_k; |
| 867 | vkNorm = sqrt(vkNorm); |
| 868 | |
| 869 | |
| 870 | double alpha = -signum(vk_k) * vkNorm; |
| 871 | vk_k -= alpha; |
| 872 | vk[k] = vk_k; |
| 873 | beta += vk_k*vk_k; |
| 874 | |
| 875 | |
| 876 | if(beta == 0) |
| 877 | continue; |
| 878 | double TwoOverBeta = 2.0/beta; |
| 879 | qrUpdateQ(Q, k, vk, TwoOverBeta); |
| 880 | qrUpdateR(k, N, A, vk, TwoOverBeta, M); |
| 881 | } |
| 882 | qr[0] = Q; |
| 883 | if(isSquare()) |
| 884 | { |
| 885 | A.mutableTranspose(); |
| 886 | qr[1] = A; |
| 887 | } |
| 888 | else |
| 889 | qr[1] = A.transpose(); |
| 890 | return qr; |
| 891 | } |
| 892 | |
| 893 | private class QRRun implements Runnable |
| 894 | { |
no test coverage detected