![]() |
1. Заголовок или название темы должно быть информативным
2. Все тексты программ должны помещаться в теги [CODE=asm] [/CODE]
3. Прежде чем задавать вопрос, см. "FAQ",если там не нашли ответа, воспользуйтесь ПОИСКОМ, возможно, такую задачу уже решали!
4. Не предлагайте свои решения на других языках, кроме Ассемблера. Исключение только с согласия модератора.
5. НЕ используйте форум для личного общения! Все, что не относиться к обсуждению темы - на PM!
6. Проверяйте программы перед тем, как выложить их на форум!!
![]() ![]() |
![]() |
marwell |
![]() ![]()
Сообщение
#1
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
доброго дня
необходимо вычислить интеграл методом прямоугольников (ассемблерная вставка в Delphi или в паскаль) сам метод мне понятен но, на каждом шаге мне нужно будет вычислять значение функции в определенной точке. хотел было использовать макросы но не тут то было, ни паскаль ни Delphi макросы не принимают может я неправильно описываю эти макросы? var n,a,b: integer;
res, h, x: real;
begin
readln(n);
a:=0;
b:=1;
asm
fild b
fisub a
fidiv n
call funct
funct proc
...
[Error] Project1.dpr(18): Undeclared identifier: 'funct' думал что макросы описываются след образом: <имя> macro парам1, парам2... парам N ... ...набор команд ... endm |
IUnknown |
![]()
Сообщение
#2
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
MACRO встроенным ассемблером не поддерживается. Поддерживаются инструкции, а не препроцессор. Используй функции.
|
marwell |
![]()
Сообщение
#3
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
var n,a,b: integer;
res, h, x: real;
begin
readln(n);// ввод количества частичных отрезков
a:=0; // a и b - границы
b:=1;
x:=0; // частичная сумма
res:=0;
asm
fild b // загрузка b на вершину стека
fisub a // b-a
fidiv n // :n
fst h // значение из вершины в h
mov ecx,n
@m: fld x
fadd h
fst x
fptan
fdivr st(1),st
fadd res
fst res
loop @m;
end
writeln(res:5:4);
readln;
end.
почему происходит деление на ноль? я же прибавляю перед делением h fld x
fadd h
|
marwell |
![]()
Сообщение
#4
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
аа, дело в
fdivr st(1),st
кажется там на каждом шаге номер меняется? на первом шаге надо st(5) делить на st(6)? или я неправильно понял структуру стека? Сообщение отредактировано: marwell - 24.05.2012 14:32 |
IUnknown |
![]()
Сообщение
#5
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
|
marwell |
![]()
Сообщение
#6
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
сорри, успел отредактировать свое предыдущее сообщение до того как увидел ваш ответ
а насчет прикрепленной картинки, как то не очень понятно ![]() Добавлено через 6 мин. на каком то шаге тангенс равен 0? |
IUnknown |
![]()
Сообщение
#7
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
Посмотри на содержимое стека FPU. Сколько там осталось свободных регистров? Нисколько. Вот поэтому и вылет: переполнение стека FPU. Чистить стек нужно.
|
marwell |
![]()
Сообщение
#8
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
спасибо!
var n,a,b: integer;
res, h, x: real;
begin
readln(n);// ââîä êîëè÷åñòâà ÷àñòè÷íûõ îòðåçêîâ
a:=0; // a è b - ãðàíèöû
b:=1;
x:=0; // ÷àñòè÷íàÿ ñóììà
res:=0;
asm
fild b // çàãðóçêà b íà âåðøèíó ñòåêà
fisub a // b-a
fidiv n // :n
fstp h // çíà÷åíèå èç âåðøèíû â h
mov ecx,n
@m: fld x
fadd h
fst x
fptan
fdivr st(1),st
fadd res
fstp res
finit
loop @m;
end
writeln(res:5:4);
readln;
end.
осталось понять почему считает неправильно. res почему то всегда равен введенному n |
IUnknown |
![]()
Сообщение
#9
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
Функция какая у тебя, тангенс или котенгенс? Если тангенс - то вот так:
asm
fild b
fisub a
fidiv n
fst h
mov ecx, n
fld x
@m:
fadd st(1)
fld st(0) // Дублируем значение Х
fptan
fdivp st(1),st
fadd res
fstp res
loop @m;
end
writeln(res:5:4);
(логика очень проста: в стеке держим только приращение в ST1, и текущее значение X в ST0, все остальное сразу после вычисления убираем). Если функция - КОтангенс - поменяй fdivp на fdivrp |
marwell |
![]()
Сообщение
#10
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
Функция какая у тебя, тангенс или котенгенс? Если тангенс - то вот так: asm
fild b
fisub a
fidiv n
fst h
mov ecx, n
fld x
@m:
fadd st(1)
fld st(0) // Дублируем значение Х
fptan
fdivp st(1),st
fadd res
fstp res
loop @m;
end
writeln(res:5:4);
(логика очень проста: в стеке держим только приращение в ST1, и текущее значение X в ST0, все остальное сразу после вычисления убираем). Если функция - КОтангенс - поменяй fdivp на fdivrp спасибо! да, тангенс нужен. И логика понятна. Только Delphi ругается на эту строчку fadd st(1)
говорит [Error] Project1.dpr(25): Invalid combination of opcode and operands |
IUnknown |
![]()
Сообщение
#11
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
FPC не ругается, в Дельфи сейчас посмотрю.
Update Да, замени ту строку вот на эту: fadd st, st(1)
Сообщение отредактировано: IUnknown - 24.05.2012 16:32 |
marwell |
![]()
Сообщение
#12
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
FPC не ругается, в Дельфи сейчас посмотрю. Update Да, замени ту строку вот на эту: fadd st, st(1)
сделал. Запускается без ошибок. Вот только ответ... Ответ должен быть приблизительно 0.261168 да? А прога при n=100 выдает 62,3434. Чем больше n, тем дальше ответ растет ![]() |
IUnknown |
![]()
Сообщение
#13
|
![]() a.k.a. volvo877 ![]() ![]() ![]() ![]() ![]() Группа: Пользователи Сообщений: 1 013 Пол: Мужской Репутация: ![]() ![]() ![]() |
Не верю
![]() program Project1;
{$APPTYPE CONSOLE}
uses math;
var n, a, b: integer;
res, h, x: real;
i : Integer;
begin
// readln(n);
n := 15000;
a := 0;
b := 1;
x := 0;
res := 0;
asm
fild b
fisub a
fidiv n
fst h
mov ecx, n
fld x
@m:
fadd st, st(1)
fld st(0)
fptan
fdivp st(1), st
fadd res
fstp res
loop @m;
fld res
fmul st, st(2)
fstp res
end
writeln(res:5:4);
// Test
h := (b - a) / n;
x := 0;
res := 0;
for i := 1 to n do
begin
x := x + h;
res := res + tan(x);
end;
res := res * h;
writeln(res:5:4);
readln;
end.
Чем выше N - тем выше точность. А так значения абсолютно одинаковые.Сообщение отредактировано: IUnknown - 24.05.2012 17:42 |
marwell |
![]()
Сообщение
#14
|
Бывалый ![]() ![]() ![]() Группа: Пользователи Сообщений: 198 Пол: Мужской Репутация: ![]() ![]() ![]() |
Не верю ![]() program Project1;
{$APPTYPE CONSOLE}
uses math;
var n, a, b: integer;
res, h, x: real;
i : Integer;
begin
// readln(n);
n := 15000;
a := 0;
b := 1;
x := 0;
res := 0;
asm
fild b
fisub a
fidiv n
fst h
mov ecx, n
fld x
@m:
fadd st, st(1)
fld st(0)
fptan
fdivp st(1), st
fadd res
fstp res
loop @m;
fld res
fmul st, st(2)
fstp res
end
writeln(res:5:4);
// Test
h := (b - a) / n;
x := 0;
res := 0;
for i := 1 to n do
begin
x := x + h;
res := res + tan(x);
end;
res := res * h;
writeln(res:5:4);
readln;
end.
Чем выше N - тем выше точность. А так значения абсолютно одинаковые.большое и уже не первое спасибо ![]() |
Fresselasuits |
![]()
Сообщение
#15
|
Группа: Пользователи Сообщений: 1 Пол: Женский Реальное имя: 23545678 Репутация: ![]() ![]() ![]() |
И всётаки, как в Delphi, с помощью asm можно вызвать прерывание, например int 31h ? Очень надо
|
![]() ![]() |
![]() |
Текстовая версия | 17.07.2025 22:49 |