Помогите , пожалуйста, с ассемблером в программе турбо паскаль
не могу правильно написать программу, а точнее поделить
var
s:word;
c:integer;
begin
writeln('найти сумму s=x^3/2+1 при x[0,40]');
asm
mov cx, 2
mov dx, 0
mov bx, 0
@1:
add dl, 1
mov al, dl
mul dl
mul dl
mov bl, dl
mov bl, 2
div bl
add ax, 1
add bx,ax
loop @1
mov s, bx
end;
writeln ('s:= ',s);
end.
Ответы (1 шт):
Автор решения: Anton Shchyrov
→ Ссылка
mov cx, 2
Записали в cx 2
mul dl
умножили AL на DL, результат положили в AX
mul dl
опять умножили AL на DL, результат положили в AX, то что было в AH потеряли
mov bl, dl mov bl, 2
вначале в BL записали значение DL, потом записали в BL 2. Вопрос - зачем записывали DL?
loop @1
уменьшили значение CX, и если оно не стало равно нулю, то начали еще одну итерацию. Вопрос, сколько у нас выполнится итераций, если вы вначале выполнили mov cx, 2?
Далее, общее замечание, в ассемблерных вставках вы можете свободно модифицировать три регистра AX, CX, DX. Значение остальных регистров, если вы их модифицируете, нужно восстановить.
Теперь правильный код.
function sum: Word; assembler;
asm
push bx { сохраним регистр bx }
xor bx, bx { обнулили регистр bx. Здесь будем собирать итоговую сумму }
mov cx, 40 { записали в cx, количество итераций. Одновременно это будет текущее значение x }
@1:
mov ax, cx
mul cx { умножаем ax на cx. Результат будет в паре dx:ax. Но для X <= 40 нам хватит и 2 байт }
mul cx
shr ax, 1 { сдвигаем ax на один бит вправо, что эквивалентно делению на 2 }
inc ax { добавляем к ax 1 }
add bx, ax { суммируем с аккумулятором }
loop @1 { уменьшили значение cx, и если оно не стало равно нулю, то начали еще одну итерацию }
inc bx { мы пропустили итерацию при x = 0. Добавляем значение 0^3/2+1=1 }
mov ax, bx { результат функции возвращаем через ax }
pop bx { восстанавливаем значение bx }
end;
begin
writeln ('s:= ', sum);
end.