fork download
  1.  
  2. #include <iostream>
  3. #include <iomanip>
  4.  
  5. #include <boost/numeric/ublas/lu.hpp>
  6. #include <boost/numeric/ublas/matrix.hpp>
  7. #include <boost/numeric/ublas/vector.hpp>
  8. #include <boost/numeric/ublas/io.hpp>
  9.  
  10. #define EQUATIONS_COUNT 3
  11.  
  12. #define COEFFICIENTS \
  13. 3.0, -5.0, 1.0,\
  14. 2.0, 1.0, 2.0,\
  15. 1.0, -1.0, 1.0
  16.  
  17. #define CONSTANT_TERMS \
  18. 1.0,\
  19. 5.0,\
  20. 3.0
  21.  
  22. //#define DEBUG // uncomment to debug
  23.  
  24. using namespace boost::numeric::ublas;
  25.  
  26. #define DECL_VALUES_ARRAY(NAME, SIZE, ...)\
  27. double arr_##NAME[SIZE] = { __VA_ARGS__ };\
  28. std::vector<double> NAME;\
  29. NAME.assign(arr_##NAME, arr_##NAME + SIZE);
  30. typedef matrix<double, row_major, std::vector<double>> Matrix;
  31. typedef vector<double, std::vector<double>> Vector;
  32.  
  33. void printMatrix(const std::string & text, Matrix & printingMatrix){
  34. std::cout << text << "[" << printingMatrix.size1() << "]" << "[" << printingMatrix.size2() << "](" <<std::endl;
  35. for(unsigned int iIndex = 0; iIndex < printingMatrix.size1(); ++iIndex){
  36. std::cout << "( ";
  37. for(unsigned int jIndex = 0; jIndex < printingMatrix.size2(); ++jIndex){
  38. std::cout<<printingMatrix(iIndex, jIndex)<<" ";
  39. }
  40. std::cout << ")," << std::endl;
  41. }
  42.  
  43. std::cout << ")" << std::endl << std::endl;
  44. }
  45.  
  46. void printEquationsSystem(const std::string & text, Matrix & printingMatrix, Vector& printingVector){
  47. std::cout << text << "{" << std::endl;
  48. for (unsigned int iIndex = 0; iIndex < printingMatrix.size1(); ++iIndex){
  49. unsigned char printedPrev = 0;
  50. for (unsigned int jIndex = 0; jIndex < printingMatrix.size2(); ++jIndex){
  51. double elementValue = printingMatrix(iIndex, jIndex);
  52. if (jIndex && printedPrev){
  53. if (elementValue > 0){
  54. std::cout << " + ";
  55. }
  56. else if (elementValue < 0){
  57. std::cout << " - ";
  58. }
  59. //else{} // nothing
  60. }
  61. if (elementValue > 0 || (!printedPrev && elementValue)){ // ( ... && ... ) - added for removing clang warning
  62. if (elementValue != -1. && elementValue != 1.) {
  63. std::cout << printingMatrix(iIndex, jIndex) << "*";
  64. }
  65. std::cout << "X" << jIndex + 1;// << " ";
  66. printedPrev = ~0;
  67. }
  68. else if (printingMatrix(iIndex, jIndex) < 0){
  69. if (elementValue != -1.) {
  70. std::cout << -printingMatrix(iIndex, jIndex) << "*";
  71. }
  72. std::cout << "X" << jIndex + 1;// << " ";
  73. printedPrev = ~0;
  74. }
  75. //else{} // nothing
  76. }
  77. std::cout << " = " << printingVector(iIndex) << ";" << std::endl;
  78. }
  79.  
  80. std::cout << "}" << std::endl << std::endl;
  81. }
  82.  
  83. void printSolutionSet(const std::string & text, Vector & printingVector){
  84. std::cout << text << "{" << std::endl;
  85. for (unsigned int index = 0; index < printingVector.size(); ++index){
  86. unsigned char printedPrev = 0;
  87. std::cout << "X" << index + 1 << " = " << printingVector(index) << ";" << std::endl;
  88. }
  89.  
  90. std::cout << "}" << std::endl << std::endl;
  91. }
  92.  
  93. Matrix invertMatrix(const Matrix & matrixA){
  94. Matrix copyMatrixA(matrixA);
  95. //permutation_matrix<decltype(copyMatrixA)::size_type> permutationMatrixA(copyMatrixA.size1()); // ? // only for C++11
  96. permutation_matrix<Matrix::size_type> permutationMatrixA(copyMatrixA.size1());
  97. size_t res = lu_factorize(copyMatrixA, permutationMatrixA);
  98. if(res != 0){
  99. throw std::logic_error("lu_factorize error");
  100. }
  101.  
  102. Matrix inverseMatrixA(identity_matrix<double>(copyMatrixA.size1())); // Identity matrix
  103. lu_substitute(copyMatrixA, permutationMatrixA, inverseMatrixA);
  104.  
  105. return inverseMatrixA;
  106. }
  107.  
  108. int main(int argc, char** argv){
  109. try{
  110. std::cout << std::fixed;
  111.  
  112. // A
  113. DECL_VALUES_ARRAY(matrixA_values, EQUATIONS_COUNT * EQUATIONS_COUNT, COEFFICIENTS);
  114. Matrix matrixA(EQUATIONS_COUNT, EQUATIONS_COUNT, matrixA_values);
  115.  
  116. // b
  117. DECL_VALUES_ARRAY(vectorB_values, EQUATIONS_COUNT, CONSTANT_TERMS);
  118. Vector vectorB(EQUATIONS_COUNT, vectorB_values);
  119.  
  120. // A^-1
  121. auto invertedMatrixA = invertMatrix(matrixA);
  122.  
  123. // x = A^-1 * b
  124. Vector vectorX = prod(invertedMatrixA, vectorB);
  125.  
  126. #ifdef DEBUG
  127. printMatrix("matrixA: ", matrixA);
  128. std::cout << "vectorB: " << vectorB << std::endl << std::endl;
  129. printMatrix("invertedMatrixA: ", invertedMatrixA);
  130. std::cout << "vectorX: " << vectorX << std::endl << std::endl;
  131. #endif
  132. printEquationsSystem("System of equations: ", matrixA, vectorB);
  133. printSolutionSet("Solving system of equations: ", vectorX);
  134. }
  135. catch(std::exception& ex){
  136. std::cout << ex.what() << std::endl;
  137. }
  138.  
  139. #ifdef __linux__
  140. std::cout << "Press any key to continue . . . " << std::endl;
  141. (void)getchar();
  142. #elif defined(_WIN32)
  143. system("pause");
  144. #else
  145. #endif
  146.  
  147. return 0;
  148. }
Success #stdin #stdout 0.01s 5484KB
stdin
Standard input is empty
stdout
System of equations: {
3.000000*X1 - 5.000000*X2 + X3 = 1.000000;
2.000000*X1 + X2 + 2.000000*X3 = 5.000000;
X1 - X2 + X3 = 3.000000;
}

Solving system of equations: {
X1 = -1.666667;
X2 = -0.333333;
X3 = 4.333333;
}

Press any key to continue . . .