Logo Море(!) аналитической информации!
IT-консалтинг Software Engineering Программирование СУБД Безопасность Internet Сети Операционные системы Hardware
Архив форумов ЦИТФорума
Море(!) вопросов - Море(!) ответов
 
 FAQFAQ   ПоискПоиск   ПользователиПользователи   ГруппыГруппы   РегистрацияРегистрация 
 ПрофильПрофиль   Войти и проверить личные сообщенияВойти и проверить личные сообщения   ВходВход 
Как правильно задавать вопросы

рисование фрактала

 
Перейти:  
Этот форум закрыт, вы не можете писать новые сообщения и редактировать старые.   Эта тема закрыта, вы не можете писать ответы и редактировать сообщения.    Список форумов Архив форумов ЦИТФорума -> Программирование
Предыдущая тема :: Следующая тема  
Автор Сообщение
st063



Зарегистрирован: 14.06.2007
Сообщения: 2

СообщениеДобавлено: Чт Июн 14 2007 23:46    Заголовок сообщения: рисование фрактала Ответить с цитатой

Задание такое: нарисовать фрактал на множестве Мондельброта (Жулиа)
по формуле которую задаёт пользователь. среда разработки Visual C++
6.0.
Проблема заключается в том, как сделать так чтобы по формуле, введённой пользователем рисовался фрактал. Поясню:
формулу я считываю в строчном формате, упрощаю её по обратной польской записи, опять собираю, получаю формулу без скобок.
(формула не содержит никаких орераций, кроме +,-,*,/)
Пример:
x=(x+c)*(x*c-x) -> x*x*c-x*x+x*c*c-x*c
Все бы ничего, но я всё равно получаю строку. А вот как сделать так, чтобы программа работала со строкой я не знаю (ведь и "x" и "c" -комплексные и просто подставить не получается). В поисках решения написал свой класс complex, перегрузил орераторы для типов данного класса и думал всё, но нет. Я всё равно не могу использовать строку как формулу, как я не разбирал строку по символам и знакам. Кто знает, как можно это сделать подскажите, хотя бы алгоритм!!!!
И не знает ли кто-нибудь существует в C++ встроенная функция на подобии eval() в javascript, т.е. функция позволяющая обращаться к строке, как к формуле???!!!!
Вернуться к началу
Посмотреть профиль Отправить личное сообщение
Kefir



Зарегистрирован: 16.04.2005
Сообщения: 443
Откуда: Пермь

СообщениеДобавлено: Пт Июн 15 2007 05:54    Заголовок сообщения: Ответить с цитатой

Во-первых, алгоритм обратной польской записи реализован неверно.
Во-вторых, в C++ есть класс "std:complex<double>" для реализации комплексных чисел.
_________________
Самоловских Виталий aka Kefir
Вернуться к началу
Посмотреть профиль Отправить личное сообщение Отправить e-mail
st063



Зарегистрирован: 14.06.2007
Сообщения: 2

СообщениеДобавлено: Пт Июн 15 2007 08:31    Заголовок сообщения: Ответить с цитатой

Я знаю про встроенный класс в с++, но работать предпочёл со своим, ибо
нужны только операции +,-,*/ для комплексных чисел(класс мой работает правильно, проверял на конкретных примерах).
По поводу польской записи, почему не правильно? я просто в примере привёл уже конечный результат, после оптимизации польской записи.
Пример:
x=(x+c)*(x*c-x) -> (польская запись) xc+*xc*x- ->(после оптимизации получаю упрощённое вырожение) x*x*c+c*x*c-x*x-c*x.
И не было бы проблем, если 'x' и 'c' были бы числами, просто заменяешь их в просе сборки на числа, а потом переводишь строку в число с плавающей точкой встроенной функцией Convert. Но я то работаю с комплексными числами, и как перевести char * в complex не знаю.
В этом и проблема.
Вернуться к началу
Посмотреть профиль Отправить личное сообщение
Kefir



Зарегистрирован: 16.04.2005
Сообщения: 443
Откуда: Пермь

СообщениеДобавлено: Пт Июн 15 2007 08:52    Заголовок сообщения: Ответить с цитатой

Не понимаю, почему Вы предпочли свой класс, в то время как есть готовый.

Правильно выражение в обратной польской записи запишется как:

xc+xc*x-*

Парсится запроста. Только нужно реализовать стэк. Т.е. даже реализовывать не нужно. Нужно только воспользоваться.

Если встречается символ x или c, то значение соответствующее одной из этих переменных помещается в стек.

Если встречается +, достаются 2 значения из стэка, суммируются и результат помещается в стек.

Аналогично для -,*,/
_________________
Самоловских Виталий aka Kefir
Вернуться к началу
Посмотреть профиль Отправить личное сообщение Отправить e-mail
vir



Зарегистрирован: 17.05.2007
Сообщения: 24

СообщениеДобавлено: Чт Июн 21 2007 11:00    Заголовок сообщения: Ответить с цитатой

Чёт даже интересно стало, как люди вообще на С++ что-то пишут, решил вот попробовать. Вот что получилось. Код не тестировался, набирался в блокноте.
Код:

typedef Env map<string, complex<double> >;
class Expr {public: virtual complex<double> eval (Env env) const = 0;}
class EBin : public Expr {
    public: comlex<double> getA() const { return this->a->eval () };
            comlex<double> getB() const { return this->b->eval () };
    protected: EBin (Expr *a, Expr *b) {
                      this->a = a;
                      this->b = b;
               }
    private: Expr *a;
             Expr *b;
}
class EAdd : public EBin {
    public: EAdd (comlex<double> a, comlex<double> b) : EBin (a, b) {};
            complex<double> eval (Env env) const {
                return this->getA () + this-> getB ();
            }
}
class EMul : public EBin {
    public: EAdd (comlex<double> a, comlex<double> b) : EBin (a, b) {};
            complex<double> eval (Env env) const {
                return this->getA () * this-> getB ();
            }
}
class ESub : public EBin {
    public: EAdd (comlex<double> a, comlex<double> b) : EBin (a, b) {};
            complex<double> eval (Env env) const {
                return this->getA () - this-> getB ();
            }
}
class EDiv : public EBin {
    public: EAdd (comlex<double> a, comlex<double> b) : EBin (a, b) {};
            complex<double> eval (Env env) const {
                return this->getA () / this-> getB ();
            }
}
class ELit : public Expr {
    public: ELit (comlex<double> val) { this->val = val }
            complex<double> eval (Env env) const {
                return this->val;
            }
    private: complex<double> val;
}
class EVar : public Expr {
    public: EVar (string name) { this->val = val }
            complex<double> eval (Env env) const { return env[name]; }
    private: complex<double> val;
}

struct ParseRes {
   Expr *val;
   char *rest;
}
ParseRes parse (char *exp)
{
    ParseRes res, next;
    res = parse_mul (exp);
    if (res.rest == exp)
        return res;
    for (;;) {
        if (res.rest == '+') {
            next = parse_mul (res.rest + 1);
            res.val = new EAdd (res.val, next.val);
            res.rest = next.rest
        } if (res.rest == '-') {
            next = parse_mul (res.rest + 1);
            res.val = new ESub (res.val, next.val);
            res.rest = next.rest
        } else
            break;
    }
    return res;
}

ParseRes parse_mul (char *exp)
{
    ParseRes res, next;
    res = parse_mul (exp);
    if (res.rest == exp)
        return res;
    for (;;) {
        if (res.rest == '*') {
            next = parse_other (res.rest + 1);
            res.val = new EMul (res.val, next.val);
            res.rest = next.rest
        } if (res.rest == '/') {
            next = parse_other (res.rest + 1);
            res.val = new EDiv (res.val, next.val);
            res.rest = next.rest
        } else
            break;
    }
    return res;
}

ParseRes parse_other (char *exp)
{
    ParseRes res, next;
    res.rest = exp;
    res.val = NULL;
    if (isalpha (*exp)) {
        string name = new string ("");
        name += *exp++;
        while (isalphanum (*exp))
           string name += *exp++;
        res.rest = exp;
        res.val = new EVar (name);
    } else if (isdigit (*exp)) {
        complex<double> n = new complex<double> (0);
        n += *exp++ - '0';
        while (isdigit (*exp)) {
            n *= 10;
            n += *exp++ - '0';
        }
        if (*exp == '.') {
            exp++;
            int k = 1;
            while (isdigit (*exp)) {
                n *= 10;
                k *= 10;
                n += *exp++ - '0';
            }
            n /= k;
        }
        res.rest = exp;
        res.val = new ELit (n);
    } else if (*exp == '(') {
        exp++;
        next = parse (exp);
        if (next.rest[0] == ')') {
            res.rest = next.rest + 1;
            res.val = next.val;
        }
    }
    return res;
}

int main (int argc, char **argv) {
    ParseRes res;
    res = parse (argv[1]);
    Env env = new Env ();
    env["i"] = new complex<double> (0, 1);
    cout << res.val->eval (env) << endl;
}
Вернуться к началу
Посмотреть профиль Отправить личное сообщение
Показать сообщения:   
Этот форум закрыт, вы не можете писать новые сообщения и редактировать старые.   Эта тема закрыта, вы не можете писать ответы и редактировать сообщения.    Список форумов Архив форумов ЦИТФорума -> Программирование Часовой пояс: GMT + 3
Страница 1 из 1

 
Перейти:  
Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете голосовать в опросах


Powered by phpBB © 2001, 2002 phpBB Group
Русская поддержка phpBB

 

IT-консалтинг Software Engineering Программирование СУБД Безопасность Internet Сети Операционные системы Hardware

Информация для рекламодателей PR-акции, размещение рекламы — adv@citforum.ru,
тел. +7 495 6608306, ICQ 232284597
Пресс-релизы — pr@citforum.ru
Послать комментарий
Информация для авторов
This Web server launched on February 24, 1997
Copyright © 1997-2000 CIT, © 2001-2006 CIT Forum
Внимание! Любой из материалов, опубликованных на этом сервере, не может быть воспроизведен в какой бы то ни было форме и какими бы то ни было средствами без письменного разрешения владельцев авторских прав. Подробнее...