Форум программистов «Весельчак У»
  *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

  • Рекомендуем проверить настройки временной зоны в вашем профиле (страница "Внешний вид форума", пункт "Часовой пояс:").
  • У нас больше нет рассылок. Если вам приходят письма от наших бывших рассылок mail.ru и subscribe.ru, то знайте, что это не мы рассылаем.
   Начало  
Наши сайты
Помощь Поиск Календарь Почта Войти Регистрация  
 
Страниц: [1]   Вниз
  Печать  
Автор Тема: Помогите  (Прочитано 10397 раз)
0 Пользователей и 8 Гостей смотрят эту тему.
M31
Помогающий

ua
Offline Offline

« : 16-04-2006 13:24 » 

Вот написал финкцию для поиска минимума функции
Цитата
//------------------Поиск минимума функции-----
// a,b - Вводимые границы .
float pok(float a, float b, float epsilon)
{
float c,d,d1,x1,x2,x,y1,y2;
double K=0.1;
do
{
  d=b-a;
  c=(a+b)/2;
  d1=K*(b-a)/2;
  x1=c-d1; x2=c+d1;
  y1=f(x1); y2=f(x2);
  if (y1<y2) {
     b=x2;
  }
  if (y1>y2) {
     a=x1;
  }
  if (y1==y2) {
     a=x1; b=x2;
  };
  }
  while (d>=epsilon);
  x=(x1+x2)/2;
  return x ;
}
А он нормально не хочет работать:( где я ошибся?Не понял
Записан
Finch
Спокойный
Администратор

il
Offline Offline
Пол: Мужской
Пролетал мимо


« Ответ #1 : 16-04-2006 13:52 » 

M31, Опиши суть, что именно неправильно не работает. Заодно и исходный код функции f.
Записан

Не будите спашяго дракона.
             Джаффар (Коша)
Finch
Спокойный
Администратор

il
Offline Offline
Пол: Мужской
Пролетал мимо


« Ответ #2 : 16-04-2006 13:59 » 

Эту конструкцию
Код:
if (y1<y2) {
     b=x2;
  }
  if (y1>y2) {
     a=x1;
  }
  if (y1==y2) {
     a=x1; b=x2;
  };
Можно записать так:
Код:
if (y1<=y2) 
{
     b=x2;
     if (y1==y2)   a=x1;
}
else  a=x1;
Записан

Не будите спашяго дракона.
             Джаффар (Коша)
Вад
Модератор

ru
Offline Offline
Пол: Мужской

« Ответ #3 : 16-04-2006 14:06 » 

Мне кажется, уже начинать поиск минимума не с границ интервала, а с
Код:
  x1=c-d1; x2=c+d1;
  y1=f(x1); y2=f(x2);
- это может приводить к ошибке.
Во-вторых, я не совсем понял, по какому критерию выбрано значение К - 0,1?
Записан
M31
Помогающий

ua
Offline Offline

« Ответ #4 : 16-04-2006 14:09 » 

возьмём любую функцию, например:
Код:
double f(double v)
{
  double p;
p=(v)*(v);
return p;
}
Вызов:
Код:
double  a=-1;
double  b=10;
double epsilon=0.000001;
x=pok(a,b,epsilon);
Label2->Caption = FloatToStr(x);
ответ должен быть 0, а у меня 1.33
Записан
Вад
Модератор

ru
Offline Offline
Пол: Мужской

« Ответ #5 : 16-04-2006 14:22 » new

М31, лучше опишите алгоритм. Я понимаю вот это:
Код:
double K=0.1;
do
{
  d=b-a;
  c=(a+b)/2;
  d1=K*(b-a)/2;
  x1=c-d1; x2=c+d1;
  y1=f(x1); y2=f(x2);
  if (y1<y2) {
     b=x2;
  }
  if (y1>y2) {
     a=x1;
  }
  if (y1==y2) {
     a=x1; b=x2;
  };
  }
  while (d>=epsilon);
так:
"повторяем следующий набор действий до тех пор, пока длина отрезка не стала меньше Эпсилон:
- выбираем 2 точки, равноотстоящие от центра интервала на расстояние, равное 0,05 длины интервала
- если значение в первой точке меньше, чем во второй - в качестве интервала на следующей итерации выбираем расстояние от начала интервала до второй точки
- если значение в 1 точке больше - выбираем интервал от 1 точки до конца интервала
- если значения равны, на следующей итерации интервал берём от 1 до 2 точки.

Мне кажется, максимум, на что способен данный алгоритм - нахождение локального минимума функции... Он был разработан своими силами, или это интерпретация одного из алгоритмов вычислительной математики?
Записан
M31
Помогающий

ua
Offline Offline

« Ответ #6 : 16-04-2006 14:28 » 

это интерпретация одного из алгоритмов вычислительной математики:) может посоветуешь что-то хорошее для нахождения экстремумов?(может есть какой-то уже рабочий код), а то у меня только одна книжка под руками и то что-то ничего не выходит:(((
Записан
Finch
Спокойный
Администратор

il
Offline Offline
Пол: Мужской
Пролетал мимо


« Ответ #7 : 16-04-2006 14:31 » 

Я сейчас прогнал твой пример и получил ответ    8.31428e-008. Что в принципе можно считать нулем.
Вот текст программы:
Код:
#include <math.h>
#include <iostream.h>

double f(double v)
{
return v*v;
}
//------------------Ïîèñê ìèíèìóìà ôóíêöèè-----
// a,b - Ââîäèìûå ãðàíèöû .
double pok(double a, double b, double epsilon)
{
double c,d,d1,x1,x2,x,y1,y2;
double K=0.1;
do
{
  d=b-a;
  c=(a+b)/2;
  d1=K*(b-a)/2;
  x1=c-d1; x2=c+d1;
  y1=f(x1); y2=f(x2);
  if (y1<=y2)
  {
     b=x2;
     if (y1==y2)   a=x1;
  }
  else  a=x1;
}
while (d>=epsilon);
x=(x1+x2)/2;
return x ;
}

int main()
{
cout << pok(-1.0, 10.0, 0.000001);
return 0;

}
Записан

Не будите спашяго дракона.
             Джаффар (Коша)
M31
Помогающий

ua
Offline Offline

« Ответ #8 : 16-04-2006 14:41 » 

ОПА, очень странно, да у меня тоже в консоли всё нормально:)
Записан
Вад
Модератор

ru
Offline Offline
Пол: Мужской

« Ответ #9 : 16-04-2006 16:59 » 

М31, сейчас по памяти боюсь наврать, но есть целый ряд алгоритмов для таких задач. К сожалению, конспекты по численным методам остались лежать на работе, поэтому смогу глянуть только завтра.
Можешь выложить оригинал алгоритма?
Записан
Страниц: [1]   Вверх
  Печать  
 

Powered by SMF 1.1.21 | SMF © 2015, Simple Machines