Advertisement
Gistrec

asm lab 3

Dec 3rd, 2018
198
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. /**
  2.  * Программа находит решение уравнения ln((x - 1) / 3) / 3 = 0
  3.  * методом Ньютона с подвижным полюсом
  4.  */
  5.  
  6. /******** MAIN.CPP ********/
  7. #include <iostream> // cin, cout
  8. #include <iomanip>  // setprecision
  9.  
  10. using std::cout;
  11. using std::endl;
  12.  
  13. /**
  14.  * Процедура реализует метод 'Ньютона с подвижным полюсом'
  15.  * Возвращает значение X в уравнении ln((x - 1) / 3) / 3 = 0
  16.  * С точностью |X - nextX| < accuracy
  17.  */
  18. extern "C" void __fastcall calculate();
  19.  
  20. extern "C" float X     = 1.5f; // Начальное значение
  21. extern "C" float NextX = NULL; // Следующее значение функции
  22.  
  23. extern "C" float accurecy = 1e-6f; // Точность |X - NextX|
  24.  
  25. int main() {
  26.     cout << X << endl;
  27.  
  28.     calculate();
  29.     cout << std::setprecision(10) << NextX << endl;
  30.  
  31.     return 0;
  32. }
  33.  
  34.  
  35.  
  36. /******** FUNCT.ASM ********/
  37. .386
  38. .MODEL FLAT;
  39.  
  40. EXTERN _X: DWORD
  41. EXTERN _NextX: DWORD
  42. EXTERN _accurecy: DWORD
  43.  
  44. .DATA
  45. BUFFER DWORD 0.0
  46. THREE  DWORD 3.0 ; Константа 3
  47. TWO    DWORD 2.0 ; Константа 2
  48. .CODE
  49.  
  50. ; Получаем значение функции  f(x) = ln((x - 1) / 3) / 3
  51. ; Постфиксная запись         f(x) = x 1 - 3 / ln 3 /
  52. ; Входное значение    _X
  53. ; Выходное значение   BUFFER
  54. getF PROC
  55. fld1 ; Для логарифма...
  56.  
  57. FLD _X ; Загружаем X
  58. FLD1   ; Загружаем 1
  59. FSUB   ; Отнимаем от X, 1
  60.  
  61. FLD THREE ; Загружаем в стек 3
  62. FDIV      ; Делим первый раз на три
  63.  
  64. ; Натуральный логарифм X = ln(X) = ln(2) * log2(X) = fyl2x(fldln2, X)
  65. ; URL: http://www.cyberforum.ru/assembler/thread525843.html
  66. FYL2X  ; st(0) = st(1) * log2( st(0) )
  67. FLDLN2 ; st(0) = ln(2)   st(1) = (X - 1) / 3
  68. FMUL
  69.  
  70. FLD THREE ; Загружаем в стек 3
  71. FDIV      ; Делим второй раз на три
  72.  
  73. FSTP BUFFER ; Сохраняем значение в переменную BUF
  74.  
  75. RET
  76. getF ENDP
  77.  
  78. ; Получаем значение производной функции   fdx(x) = 1 / (3 * (x - 1))
  79. ; Постфиксная запись                      fdx(x) = 1 3 x 1 - * /
  80. ; Входное значение    _X
  81. ; Выходное значение   BUFFER
  82. getFdx PROC
  83. FLD1
  84. FLD THREE
  85. FLD _X
  86. FLD1
  87. FSUB
  88. FMUL
  89. FDIV
  90.  
  91. FSTP BUFFER
  92.  
  93. RET
  94. getFdx ENDP
  95.  
  96. ; Получаем значение      xk+1 = xk + f(xk) * (f(xk) - 2) / 2 * fdx(xk)
  97. ; Постфиксная запись     xk+1 = xk f(xk) f(xk) 2 - * 2 / fdx(xk) * +
  98. ; Входное значение  (xk)     _X
  99. ; Выходное значение (xk+1)   _NextX
  100. next PROC
  101. FLD _X ; Загружаем X
  102.  
  103. call getF  ; Вычисляем f(xk)
  104. FLD BUFFER ; Загружаем f(xk)
  105. FLD BUFFER
  106.  
  107. FLD TWO
  108. FSUB
  109. FMUL
  110. FLD TWO
  111. FDIV
  112.  
  113. call getFdx  ; Вычисляем fdx(xk)
  114. FLD BUFFER   ; Загружаем fdx(xk)
  115.  
  116. FMUL
  117. FADD
  118.  
  119. FSTP _NextX
  120.  
  121. RET
  122. next ENDP
  123.  
  124. @calculate@0 PROC
  125. ; Инициализируем сопроцессор
  126. FINIT
  127. call next;
  128.  
  129. @start:
  130. FLD _X                      ;
  131. FLD _NextX                  ;    Сравниваем точность нашего решения, которая вычисляется
  132. FSUB                        ;    по формуле |_X - _NextX|
  133. FABS                        ;    с заданной точностью, которая хранится в accurecy
  134.                             ;
  135. FLD _accurecy               ;
  136. FCOMIP ST(0), ST(1)         ;
  137.                             ;    Если наше реiение точно, то переходим на метку @exit
  138. JNC @exit                   ;    Иначе продолжаем цикл
  139.  
  140.  
  141. MOV EAX, _NextX
  142. call next         ; Получаем xk+1
  143. MOV _X, EAX
  144. call next ; Какого хуя это тут нужно?!
  145. loop @start
  146.  
  147.  
  148. @exit:
  149. RET
  150. @calculate@0 ENDP
  151.  
  152.  
  153. END
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement