Модераторы: Daevaorn

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> подскажите что плохого в этом проектировании 
:(
    Опции темы
Alek86
Дата 5.11.2007, 23:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



есть такая ситуация.
существует класс Channel, который получается путем разбора строк файла.
у него есть Name и список Event'ов (так называется программа или фильм)

файл должен иметь примерно такой вид:

Код

ch: Интер
06:30 Новости
07:00 Подьем
07:30 Кофе в постель
...
01:20 Х/ф "Горячие тройняшки"


но, поскольку файл пишется человеком, то возможны опечатки и какая-то строка не будет подходить под общий вид Event'а, и поэтому будет считаться мусором (Garbage). Но и мусор мне также нужно хранить, чтобы человек его мог исправить.

Иерархия у меня такова:

Код

class IPart {/*реализация*/};
class Event : public IPart {/*реализация*/};
class Garbage : public IPart {/*реализация*/};
class Channel {
    /*реализация*/
    std::vector<shared_ptr<IPart> > m_Parts;
    /*реализация*/
};


для того, чтобы вывести Channel в виде строки я использую полиморфизм и вызываю функцию
Код

    std::string IPart::ToString();

для каждого элемента контейнера по очереди

но если мне нужно в классе Channel повызывать функцию, к примеру
Код

    void Event::GetTime(byte* bH, byte* bM);

для всех событий из списка, я хочу использовать dynamic_cast. Но мне тут сказали, что, скорее всего, я где-то заблуждаюсь...

Ну вот и сам вопрос - заблуждаюсь ли я где-то здесь? smile


ЗЫ Если чето неясно, уточню. К функциям не придираться, в реальности они чуть более оптимизированны.


--------------------
user posted image    user posted image
PM MAIL   Вверх
JackYF
Дата 6.11.2007, 02:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


полуавантюрист
****


Профиль
Группа: Участник
Сообщений: 5814
Регистрация: 28.8.2004
Где: страна тысячи озё р

Репутация: 18
Всего: 162



Цитата(Alek86 @  5.11.2007,  23:14 Найти цитируемый пост)
Но мне тут сказали, что, скорее всего, я где-то заблуждаюсь...

Очень точная фраза :\. smile

А так вообще - проектирование как проектирование. Можно сделать и по-другому, наверняка, но имеет, имхо, право на жизнь.


--------------------
Пожаловаться на меня как модератора можно здесь.
PM MAIL Jabber   Вверх
Alek86
Дата 6.11.2007, 08:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(JackYF @  6.11.2007,  02:06 Найти цитируемый пост)
Очень точная фраза

постараюсь поточнее:
Цитата(archimed7592 @  5.11.2007,  22:45 Найти цитируемый пост)
Насколько я понял задачу, dynamic_cast тут не приштопай, не пришей


если кому не жалко времени - как нужно сделать лучше (проще)?



--------------------
user posted image    user posted image
PM MAIL   Вверх
MAKCim
Дата 6.11.2007, 10:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Alek86, 
в IPart описать метод, который возвращает уникальное число, идентифицирующее класс объекта
в Channel вызывать его и сравнивать результат с числом, идентифицирующим нужный класс
думаю, будет эффективнее


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 6.11.2007, 11:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(Alek86 @  5.11.2007,  23:14 Найти цитируемый пост)
для всех событий из списка, я хочу использовать dynamic_cast

Ты так и не объяснил, зачем тебе нужен dynamic_cast smile

Цитата(MAKCim @  6.11.2007,  10:17 Найти цитируемый пост)
в IPart описать метод, который возвращает уникальное число, идентифицирующее класс объекта
в Channel вызывать его и сравнивать результат с числом, идентифицирующим нужный класс
думаю, будет эффективнее 

Если имеется в виду имитация RTTI посредством виртуальных вызовов, то добиться таким трюком прироста производительности можно разве что при кривом компиле, который неэффективно реализует RTTI smile Например, на MinGW я разницы не заметил (правда, сравнивал не с dynamic_cast, а с typeid).
PM MAIL   Вверх
MAKCim
Дата 6.11.2007, 12:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  6.11.2007,  11:52 Найти цитируемый пост)
Если имеется в виду имитация RTTI посредством виртуальных вызовов, то добиться таким трюком прироста производительности можно разве что при кривом компиле, который неэффективно реализует RTTI

обоснуй
GCC, к примеру, генерирует вот такой код (для вызова виртуального метода)
Код

...
; в EDX - указатель типа базового класса на объект производного класса
mov eax, dword ptr [edx] ; получаем указатель на таблицу виртуальных методов
add eax, OFFSET ; OFFSET - смещение в таблице, по которому находится адрес нужного метода
push edx ; this
jmp dword ptr [eax] ; вызов метода
...

код крайне эффективный на самом деле
RTTI можно реализовать быстрее?
соглашусь, если приведешь описание реализации в каком-нибудь компиляторе

Это сообщение отредактировал(а) MAKCim - 6.11.2007, 12:24


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
Alek86
Дата 6.11.2007, 12:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(UnrealMan @  6.11.2007,  11:52 Найти цитируемый пост)
Ты так и не объяснил, зачем тебе нужен dynamic_cast 


чтобы циклом пройтись по контейнеру и преобразовать IPart в Event, чтобы вызвать Event::GetTime


Цитата(MAKCim @  6.11.2007,  10:17 Найти цитируемый пост)
в IPart описать метод, который возвращает уникальное число, идентифицирующее класс объектав Channel вызывать его и сравнивать результат с числом, идентифицирующим нужный классдумаю, будет эффективнее


то есть, на моем месте примерно такой бы "проект" у проги и был? ведь, ка я понял, суть такая же, как и у динамик каста....


--------------------
user posted image    user posted image
PM MAIL   Вверх
UnrealMan
Дата 6.11.2007, 21:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  6.11.2007,  12:22 Найти цитируемый пост)
обоснуй

Я не вижу никаких преград для эффективной реализации оператора typeid, работу которого предполагается имитировать с помощью виртуальных вызовов.

Цитата(MAKCim @  6.11.2007,  12:22 Найти цитируемый пост)
GCC, к примеру, генерирует вот такой код (для вызова виртуального метода)

Чем строить голые теории, лучше просто замерить время, затрачиваемое на сравнение по typeid и на сравнение по id, возвращённому виртуальной функцией.

Вот грубый замер:

Код

#include <iomanip>
#include <iostream>
#include <windows.h>

typedef void (*TypeId)();

template <class T>
    struct TypeInfo
{
    static void Id() {}
};

struct Base
{
    virtual ~Base() {}
    virtual TypeId GetTypeId() { return &TypeInfo<Base>::Id; }
};

struct Derived : Base
{
    virtual TypeId GetTypeId() { return &TypeInfo<Derived>::Id; }
};

int main()
{
    const long n = 2000000000;

    DWORD time, t1, t2, drift;

    Derived derived;
    Base &base = derived;

    time = GetTickCount();
    for (long i=0; i<n; ++i)
    {
        if (typeid(base)!=typeid(Derived))
            return 0; // never return
    }
    t1 = GetTickCount() - time;

    time = GetTickCount();
    for (long i=0; i<n; ++i)
    {
        if (base.GetTypeId()!=&TypeInfo<Derived>::Id)
            return 0; // never return
    }
    t2 = GetTickCount() - time;

    time = GetTickCount();
    for (long i=0; i<n; ++i);
    drift = GetTickCount() - time;
    if (drift<10)
        std::cout << "the drift was not eliminated" << std::endl;

    // во сколько раз сравнение через виртуальный вызов быстрее сравнения через typeid
    std::cout << std::setprecision(2) << double(t1-drift)/(t2-drift) << std::endl;
}

У меня выводится 0.92 smile


Это сообщение отредактировал(а) UnrealMan - 6.11.2007, 21:10
PM MAIL   Вверх
archimed7592
Дата 6.11.2007, 21:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Ыыы, Alek86, ты в теме в которой грозишься создать другую тему предупреждай, если создаёшь smile.

Цитата(MAKCim @  6.11.2007,  10:17 Найти цитируемый пост)
в IPart описать метод, который возвращает уникальное число, идентифицирующее класс объекта
в Channel вызывать его и сравнивать результат с числом, идентифицирующим нужный класс
думаю, будет эффективнее 

Один фиг, что dynamic_cast, что это число smile. Только dynamic_cast будет работать стабильно а возвратить число можно "забыть"(или ещё как-нибудь закосячить) smile.


По теме:
1. возвращать "плохое" время в случае, если это мусор.
2. добавить возможность(если её нет) редактирования(исправления ошибок) не только мусора, но и нормальных событий(человек может написать нормально оформленный файл, но ошибиться в имени фильма, к примеру).

Тогда надобность в интерфейсе и, соответственно, в dynamic_cast'ах исчезнет.

Добавлено через 2 минуты и 6 секунд
К слову, мне сейчас много приходится работать с интерфейсами, но dynamic_cast'ами не пользуюсь, ибо, либо интерфейс включает в себя всё необходимое для взаимодействия с объектом, либо нужны разные интерфейсы/сущности(либо интерфейсы не нужны вообще).


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
Alek86
Дата 6.11.2007, 22:01 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(archimed7592 @  6.11.2007,  21:50 Найти цитируемый пост)
 ты в теме в которой грозишься создать другую тему предупреждай, если создаёшь

звыняюсь, забылся

дело-то все в том, что эти классы нужны в 2х случаях:

1. показывать ошибки человеку. Для этого надло преобразовывать в строку и кидать в ричэдит

2.
 а) проверять "логику". к примеру, отсортировать события по времени 
 б) преобразовывать то, что он начепятал, в нужный мне формат (бинарный файл)
для этого нужно манипулировать std::string'ами и byte'ами

имхо, самое "естесственное" решение тут - это чтобы 1 класс (Event) хранил в себе данные, а имел 2 интерфейса для отображения в этих 2х случаях...

может, ты подскажешь, как в этом нетрудном примере (3 класса) ты бы спроектировал прогу? хоть на пальцах, чтоб я понял, ато 
Цитата(archimed7592 @  6.11.2007,  21:50 Найти цитируемый пост)
либо интерфейс включает в себя всё необходимое для взаимодействия с объектом, либо нужны разные интерфейсы/сущности(либо интерфейсы не нужны вообще).

уж очень обтекаемо ((


--------------------
user posted image    user posted image
PM MAIL   Вверх
archimed7592
Дата 6.11.2007, 22:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(Alek86 @  6.11.2007,  22:01 Найти цитируемый пост)
1. показывать ошибки человеку. Для этого надло преобразовывать в строку и кидать в ричэдит

bool hasMistake();

Цитата(Alek86 @  6.11.2007,  22:01 Найти цитируемый пост)
а) проверять "логику". к примеру, отсортировать события по времени 

При сортировке выкидывать те которые has mistake.

Цитата(Alek86 @  6.11.2007,  22:01 Найти цитируемый пост)
б) преобразовывать то, что он начепятал, в нужный мне формат (бинарный файл)
для этого нужно манипулировать std::string'ами и byte'ами

Очень даже вписывается в предыдущие два пункта.


Цитата(Alek86 @  6.11.2007,  22:01 Найти цитируемый пост)
имхо, самое "естесственное" решение тут - это чтобы 1 класс (Event) хранил в себе данные, а имел 2 интерфейса для отображения в этих 2х случаях...

Вопрос дня: а зачем нужны аж два интерфейса? Предполагаются другие реализации этого класса?


Цитата(Alek86 @  6.11.2007,  22:01 Найти цитируемый пост)
может, ты подскажешь, как в этом нетрудном примере (3 класса) ты бы спроектировал прогу?

Опа а 3 класса откуда взялось? smile

Короче говоря, попробуй описать логику более полно, но не особо вдаваяся в ненужные подробности. Думаю ответ до тебя дойдёт сам собой, но, если не осенит, то мы обязательно тебе подскажем smile.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
Alek86
Дата 6.11.2007, 22:33 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



боюсь, сильно это долго... ((
сама эта вещь (распознание телепрограммы) большая, и я привел мелкий ее кусок для примера.

к примеру
Цитата(archimed7592 @  6.11.2007,  22:18 Найти цитируемый пост)
bool hasMistake();


не выйдет, так как пользователю инфа выдается в ричэдите, где ошибки выделены красным. а само событие "в реале" состоит их времени и имени, причем в запись времени также может вкрасться ошибка ("25:34")тогда красным выделится только "25". и так далее. то есть нужно из класса получать строку и какую-то структуру с указанием, в каких местах в этой строке ошибки, а не просто "ошибка есть".


Цитата(archimed7592 @  6.11.2007,  22:18 Найти цитируемый пост)
 а зачем нужны аж два интерфейса? Предполагаются другие реализации этого класса?

не в том дело. дело в том, что в реале и сам Channel является релизацией интерфейса IPart, поскольку есть еще и список каналов smile


Цитата(archimed7592 @  6.11.2007,  22:18 Найти цитируемый пост)
Опа а 3 класса откуда взялось?

Код

class Event : public IPart;
class Garbage : public IPart;
class Channel;



в общем, итог, по-видимому, таков. если я опишу всю проблему, даже без мелочей, то проект для ее решения будет очень немелкий. smileтак что не стОит smile. спасибо за труды smile


--------------------
user posted image    user posted image
PM MAIL   Вверх
archimed7592
Дата 6.11.2007, 22:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(Alek86 @  6.11.2007,  22:33 Найти цитируемый пост)
не выйдет, так как пользователю инфа выдается в ричэдите

Цитата(Alek86 @  6.11.2007,  22:33 Найти цитируемый пост)
то есть нужно из класса получать строку и какую-то структуру с указанием, в каких местах в этой строке ошибки, а не просто "ошибка есть".

А нельзя сразу вытягивать отформатированную строку(с указаниями ошибок, если нужно)?


Цитата(Alek86 @  6.11.2007,  22:33 Найти цитируемый пост)
не в том дело. дело в том, что в реале и сам Channel является релизацией интерфейса IPart, поскольку есть еще и список каналов smile

Нее, что-то тут не ладно... Ты не по тому признаку обобщал smile.

Цитата(Alek86 @  6.11.2007,  22:33 Найти цитируемый пост)
в общем, итог, по-видимому, таков. если я опишу всю проблему, даже без мелочей, то проект для ее решения будет очень немелкий. smileтак что не стОит smile. спасибо за труды smile 

Дам последнее напутствие.

В том виде в каком это у тебя есть сейчас(все являются наследниками IPart) - это паттерн Композиция(если немного видоизменить). По сути, к нему можно очень просто прикрутить Визитора, но там как-раз таки dynamic_cast'ы повсюду smile.

В общем, решай сам. Либо у тебя будут перенасыщенные интерфейсы, либо тебе придётся применять dynamic_cast, либо тебе придётся перепроектировать.


зы. Неужели так много телепрограмм, что падает производительность из-за применения shared_ptr/dynamic_cast? 0_o


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
MAKCim
Дата 6.11.2007, 22:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



UnrealMan, 
а если упростить код?
Код

struct Base
{
    virtual ~Base() {}
    virtual int GetTypeId() { return 0; }
};
struct Derived : Base
{
    virtual int GetTypeId() { return 1; }
};
...
for (long i=0; i<n; ++i)
    {
        if (base.GetTypeId() != 1)
            return 0; // never return
    }



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
Alek86
Дата 7.11.2007, 00:01 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(archimed7592 @  6.11.2007,  22:44 Найти цитируемый пост)
Неужели так много телепрограмм, что падает производительность из-за применения shared_ptr/dynamic_cast


не так уж и много... пока месть... вообще вопрос про падение производительности я задал не имея в виду именно этот случай. хотелось просто узнать, является ли динамик каст чем-то таким, чем не рекомендуется пользовать из-за падения производительности. А общий указатель приплюсовался в качестве довеска. а к этому случаю в том обсуждении само как-то пришло... smile

Цитата(archimed7592 @  6.11.2007,  22:44 Найти цитируемый пост)
Нее, что-то тут не ладно... Ты не по тому признаку обобщал

потому я и "закрыл" тему, поскольку хрен я смогу объяснить что именно по тому признаку, что нужно smile слишком много для этого рассказывать, а смысла в этом мало. главное, что убедился, что ничего криминального в проекте нету
так что спасибо всем за ответы

Это сообщение отредактировал(а) Alek86 - 7.11.2007, 00:03


--------------------
user posted image    user posted image
PM MAIL   Вверх
archimed7592
Дата 7.11.2007, 00:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(Alek86 @  7.11.2007,  00:01 Найти цитируемый пост)
хотелось просто узнать, является ли динамик каст чем-то таким, чем не рекомендуется пользовать из-за падения производительности.

Ыыы... Преждевременная оптимизация - корень всех зол © Дональд Кнут.
Если нет причин беспокоиться о производительности, то беспокоиться не нужно. Если причины есть, то в первую очередь беспокоиться нужно о сложности алгоритма и, уж конечно, в последнюю очередь нужно беспокоиться о быстродействии одинаковых по асимптотической сложности конструкций.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
Alek86
Дата 7.11.2007, 00:15 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(archimed7592 @  7.11.2007,  00:07 Найти цитируемый пост)
Преждевременная оптимизация - корень всех зол


он имел в виду писание кода с оптимизацией
а в моем случае это выбор алгоритма из подобных.


--------------------
user posted image    user posted image
PM MAIL   Вверх
archimed7592
Дата 7.11.2007, 00:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(Alek86 @  7.11.2007,  00:15 Найти цитируемый пост)
а в моем случае это выбор алгоритма из подобных.

Алгоритмы то с одинаковой сложность, так что выбирать можно любой smile.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
SaDFromSpb
Дата 7.11.2007, 04:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 263
Регистрация: 5.4.2006
Где: Санкт-Петербург

Репутация: 3
Всего: 3



Alek86, 
Я привык считать, что появление необходимости в dynamic_cast свидетельствует о плохом проектировании. (Хотя, разумеется, есть исключения)
Плюс, нередко, быть "насмерть" уверенным в каких-то частях проектирования, значит связывать себе руки. Когда я говорю "тут все круто, просто долго объяснять", это значит, что я просто запарился над этим думать.... А оптимальное решение в итоге показывает, как все было не круто.  smile 
По поводу данной задачи я подробно не вникал, ибо поздно. Но навскид приходит идея, что раз Event и Garbage получаются такими разными сущностями, то почему бы их не хранить раздельно в двух векторах? Или если, нужно сохранить их последовательность относительно друг друга, то в двух мэпах, типа std::map<int, Event> и std::map<int, Garbage>, где int - это абсолютный порядковый номер...


Это сообщение отредактировал(а) SaDFromSpb - 7.11.2007, 04:28


--------------------
"За исключением части, касающейся потоков, библиотека Loki написана на стандартном языке С++. Увы, это означает, что многие современные компиляторы не смогут работать с ней в полном объеме." (А. Александреску. Modern C++ design. 2001)
PM   Вверх
Alek86
Дата 7.11.2007, 08:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



Цитата(SaDFromSpb @  7.11.2007,  04:26 Найти цитируемый пост)
Плюс, нередко, быть "насмерть" уверенным в каких-то частях проектирования, значит связывать себе руки. Когда я говорю "тут все круто, просто долго объяснять", это значит, что я просто запарился над этим думать.... А оптимальное решение в итоге показывает, как все было не круто.

согласен. и более того, я ЗНАЮ, что у меня все не круто, хотя бы потому что опыта в проектировании ООП'ных приложений почти нету. Но писать огромные описания проблемы, чтоб за меня тут проектировали все полностью, не считаю нужным smile я попробовал описать кусок проблемы...


Цитата(SaDFromSpb @  7.11.2007,  04:26 Найти цитируемый пост)
раздельно в двух векторах

они не разные сущности, так что надо вкупе


Цитата(SaDFromSpb @  7.11.2007,  04:26 Найти цитируемый пост)
в двух мэпах, типа std::map<int, Event> и std::map<int, Garbage>, где int - это абсолютный порядковый номер

мое IMHO это изврат, намного похуже динамик каста. динамик каст хранит id класса и по нему можно, фактически, и отделять, а ты предлагаешь усложнить работу (и написание) класса Channel (контейнер) в несколько раз...

Добавлено через 3 минуты и 5 секунд
кстати, еще вопрос

Цитата(SaDFromSpb @  7.11.2007,  04:26 Найти цитируемый пост)
Я привык считать, что появление необходимости в dynamic_cast свидетельствует о плохом проектировании. (Хотя, разумеется, есть исключения)

я, кстати, тоже до недавнего времени так считал. и даже не помню, почему :(
ты почему так считаешь?

Это сообщение отредактировал(а) Alek86 - 7.11.2007, 08:07


--------------------
user posted image    user posted image
PM MAIL   Вверх
Lazin
Дата 7.11.2007, 09:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3820
Регистрация: 11.12.2006
Где: paranoid oil empi re

Репутация: 41
Всего: 154



Если Garbage это частный случай Event, то ИМХО намного логичней, что-бы они имели одинаковый интерфейс (это-же всего-лишь строки телепрограммы). Но нужно заюзать полиморфизм, чтобы к примеру при выводе сообщения Garbage оно как-то выделялось, и бросало исключение, а в классе исключения может быть описана ошибка. 
То-есть я предлагаю использовать общий интерфейс для Garbage и Event, а всю дополнительную функциональность класса Garbage, вынести в класс исключения. Приемущество проявится если доля объектов класса Garbage в контейнере не велика, в этом случае исключения будут генерироваться редко, а проверять dynamic_cast - ом каждый элемент будет не нужно.
PM MAIL Skype GTalk   Вверх
UnrealMan
Дата 7.11.2007, 11:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  6.11.2007,  22:55 Найти цитируемый пост)
а если упростить код?

Те же 0.92. Значимой разнице попросту неоткуда взяться.
PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 11:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  11:35 Найти цитируемый пост)
Те же 0.92. Значимой разнице попросту неоткуда взяться. 

смотрел я ассемблерный листинг...ну никак такого не может быть
typeid медленнее даже визуально по коду


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
SaDFromSpb
Дата 7.11.2007, 11:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 263
Регистрация: 5.4.2006
Где: Санкт-Петербург

Репутация: 3
Всего: 3



Цитата(Alek86 @  7.11.2007,  08:06 Найти цитируемый пост)
мое IMHO это изврат, намного похуже динамик каста. динамик каст хранит id класса и по нему можно, фактически, и отделять, а ты предлагаешь усложнить работу (и написание) класса Channel (контейнер) в несколько раз...

Хм.. Тоже верная мысль, наверное.. Тебе виднее...

Цитата(Alek86 @  7.11.2007,  08:06 Найти цитируемый пост)
я, кстати, тоже до недавнего времени так считал. и даже не помню, почему :(
ты почему так считаешь?

Ну во-первых, потому что это когда-то говорил мудрый препод  smile , во-вторых, использование dynamic_cast'а свидетельствует о том, что мы пользуемся какой-то дополнительной функциональностью (RTTI, которую кстати, опциями компилятора можно отключить), чтобы получить истинный (ну или просто более "нижний") интерфейс объекта. Оправданно ли это? Динамик кастом можно пользоваться двумя способами: 1) Приведение, когда ты точно знаешь, какой это класс на самом деле. Но если ты это знаешь, то наверное можно провести такую реорганизацию, чтобы динамик каст не понадобился. 2) Попытка приведения по очереди к нескольким подкласам с отлавливанием ошибок при неправильном приведении (сам так ни разу не пробовал, но вроде можно). - Для С++ это как-то "грязно" =). Получается в некоторых местах теряется информация о типах, когда она должна быть. Почему должна? Потому что при хорошем проектировании интерфейс всегда достаточен для контекста в котором он используется, и когда получается наоборот - это, возможно, сигнал о том, что проектирование неудачано...
Как-то так.... 

А вообще демагогия это все.  smile 


Lazin, Тоже, кстати, мысль про исключения пришла, но, как-то не стройно получается в плане логичности и понятности. И сможет ли автору помочь механизм исключений во всех случаях, где евентом оказывается гарбидж? Хотя... ему, опять же, виднее будет...



Это сообщение отредактировал(а) SaDFromSpb - 7.11.2007, 13:33


--------------------
"За исключением части, касающейся потоков, библиотека Loki написана на стандартном языке С++. Увы, это означает, что многие современные компиляторы не смогут работать с ней в полном объеме." (А. Александреску. Modern C++ design. 2001)
PM   Вверх
UnrealMan
Дата 7.11.2007, 13:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  11:43 Найти цитируемый пост)
смотрел я ассемблерный листинг...ну никак такого не может быть
typeid медленнее даже визуально по коду 

smile Вот это и говорит о том, что надо не голые теории строить (чего там визуально по коду видится), а брать тесты и проверять, как оно на самом деле будет работать.
PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 19:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  13:16 Найти цитируемый пост)
Вот это и говорит о том, что надо не голые теории строить (чего там визуально по коду видится), а брать тесты и проверять, как оно на самом деле будет работать. 

компиляторы то у нас скорее всего разные
у меня на GCC typeid работает медленнее
и что дает в таком случае практика?
если не трудно, можешь привести ассемблерный код моего примера (без TypeInfo) на твоем компиляторе



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 19:35 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  19:00 Найти цитируемый пост)
компиляторы то у нас скорее всего разные

Компилятор у меня mingw32-g++ 3.4.4, выставлена оптимизация -O3.

Цитата(MAKCim @  7.11.2007,  19:00 Найти цитируемый пост)
у меня на GCC typeid работает медленнее

Насколько?

Цитата(MAKCim @  7.11.2007,  19:00 Найти цитируемый пост)
если не трудно, можешь привести ассемблерный код моего примера (без TypeInfo) на твоем компиляторе

Я совсем не знаю ассемблер и не знаю, как можно получить ассемблерный листинг. И не хочу знать - мне это ни капельки не интересно.

PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 19:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  19:35 Найти цитируемый пост)
Насколько?

Код

#include <typeinfo>

class A {
public:
    virtual int foo() = 0;
};

class B: public A {
    virtual int foo() { return 1; }
};

class C: public A {
    virtual int foo() { return 2; }
};

int main() {
    A * a1 = new B();
    return static_cast<int>(typeid(C) == typeid(*a1));
}

Код

# times ./a
0m0.032s 0m0.012s
0m0.795s 0m0.224s

Код

#include <typeinfo>

class A {
public:
    virtual int foo() = 0;
};

class B: public A {
    virtual int foo() { return 1; }
};

class C: public A {
    virtual int foo() { return 2; }
};

int main() {
    A * a1 = new B();
    return static_cast<int>(a1 -> foo() == 2);
}

Код

# times ./a
0m0.032s 0m0.012s
0m0.601s 0m0.178s



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 19:57 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Расшифруй. Я не понимаю, чем ты мерил и что за циферки тут привёл.
PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 20:02 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  19:57 Найти цитируемый пост)
Расшифруй. Я не понимаю, чем ты мерил и что за циферки тут привёл. 

Цитата

times  Print  the  accumulated  user  and system times for the shell and for pro‐
              cesses run from the shell.  The return status is 0.

соответственно
Цитата(MAKCim @  7.11.2007,  19:48 Найти цитируемый пост)
# times ./a
0m0.032s 0m0.012s
0m0.601s 0m0.178s

user time = 0m0.601s
system time = 0m0.178s


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 20:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Можешь по-русски внятно объяснить, что ты сейчас замерил и какие результаты получил?
PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 20:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



times определяет системное время (время работы процесса в режиме ядра: обработка прерываний, системные вызовы) и пользовательское время (время работы процесса вне режима ядра, т. е то, что нам и нужно узнать)
нам необходимо пользовательское время
оно равно в первом случае 0 минут и 0.795 секунды
во втором - 0 минут и 0.601 секунды


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 20:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  20:17 Найти цитируемый пост)
нам необходимо пользовательское время
оно равно в первом случае 0 минут и 0.795 секунды

Т.е. ты хочешь сказать, что время, затрачиваемое на выполнение вот этого кода

Цитата(MAKCim @ 7.11.2007,  19:48)
Код

    A * a1 = new B();
    return static_cast<int>(typeid(C) == typeid(*a1));


составляет чуть ли не секунду?



PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 20:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



UnrealMan, 
нет
это совокупное время работы процесса вне режима ядра
которое включает в себя в частности время выполнения данного участка кода


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 20:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  20:32 Найти цитируемый пост)
нет
это совокупное время работы процесса вне режима ядра
которое включает в себя в частности время выполнения данного участка кода

И сколько же времени затрачивается на выполнение данного участка кода (а ведь именно это нас интересует, не так ли?.. вернее, даже только часть этого участка, связанная с вычислением typeid и сравнением)?

Это сообщение отредактировал(а) UnrealMan - 7.11.2007, 20:38
PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 20:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



UnrealMan, 
какая разница?
остальной код в обоих случаях идентичен
поэтому он не влияет на общий результат
грубо говоря
B + T1 = A1
B + T2 = A2
T1 - время выполнения участка кода в первом случае
T2 - во-втором
B - время выполнения остального кода
на B можно сократить, при этом общее время уменьшится на B
т. е относительный результат будут тем же, но общее время уменьшится


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 21:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  20:49 Найти цитируемый пост)
грубо говоря
B + T1 = A1
B + T2 = A2
T1 - время выполнения участка кода в первом случае
T2 - во-втором
B - время выполнения остального кода
на B можно сократить, при этом общее время уменьшится на B
т. е относительный результат будут тем же

Твои познания в математике просто поражают smile


PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 22:28 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  21:24 Найти цитируемый пост)
Твои познания в математике просто поражают

и в чем я не прав?
по существу можешь что-нибудь сказать?  smile 


Это сообщение отредактировал(а) MAKCim - 7.11.2007, 22:30


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
archimed7592
Дата 7.11.2007, 22:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(MAKCim @  7.11.2007,  22:28 Найти цитируемый пост)
и в чем я не прав?

Думаю, в этом:
Цитата(UnrealMan @  7.11.2007,  21:24 Найти цитируемый пост)
B - время выполнения остального кода

"Остальной код" не обязан в обоих случаях выполняться одинаковое кол-во времени.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
UnrealMan
Дата 7.11.2007, 22:56 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  7.11.2007,  22:28 Найти цитируемый пост)
и в чем я не прав?

Ты издеваешься что ли?

Цитата(MAKCim @  7.11.2007,  22:28 Найти цитируемый пост)
по существу можешь что-нибудь сказать?

Хорошо, скажу по существу. На современном компе typeid(С) == typeid(*a1) в среднем вычислится меньше, чем за микросекунду (результатов выполнения своего теста я ждал несколько секунд, а там по паре миллиардов итераций). Соответственно твои замеры одного-единственного вычисления (где время исчисляется миллисекундами smile) не просто не точны - они вообще никак не отражают производительность typeid и виртуального вызова.

Теперь немного о математике. С каких это пор слагаемые при делении стало возможным сокращать? smile


Это сообщение отредактировал(а) UnrealMan - 7.11.2007, 23:00
PM MAIL   Вверх
archimed7592
Дата 7.11.2007, 23:02 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(UnrealMan @  7.11.2007,  22:56 Найти цитируемый пост)
Теперь немного о математике. С каких это пор слагаемые при делении стало возможным сокращать? smile

Ты о вычитании уравнений что-нибудь слышал smile.


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
MAKCim
Дата 7.11.2007, 23:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(archimed7592 @  7.11.2007,  22:34 Найти цитируемый пост)
"Остальной код" не обязан в обоих случаях выполняться одинаковое кол-во времени. 

почему нет?
times не зря возвращает системное и пользовательское время
системное время естественно различается (прерывания всегда асинхронны и недетерминированны)
а пользовательское постоянно, если в обоих случаях выполняется одинаковая последовательность действий (а она одинаковая)
только не надо говорить, что, дескать, частота ядра CPU может различается от опыта к опыту и т. д
она то может и различаться, только вот относительный результат всегда одинаков
Цитата(UnrealMan @  7.11.2007,  22:56 Найти цитируемый пост)
Ты издеваешься что ли?

отнюдь
Цитата(UnrealMan @  7.11.2007,  22:56 Найти цитируемый пост)
Соответственно твои замеры одного-единственного вычисления (где время исчисляется миллисекундами smile) не просто не точны - они вообще никак не отражают производительность typeid и виртуального вызова.

см. выше
Цитата(UnrealMan @  7.11.2007,  22:56 Найти цитируемый пост)
Теперь немного о математике. С каких это пор слагаемые при делении стало возможным сокращать?

к словам не надо придираться
сокращать = не учитывать

Добавлено через 2 минуты и 50 секунд
Цитата(UnrealMan @  7.11.2007,  22:56 Найти цитируемый пост)
На современном компе typeid(С) == typeid(*a1) в среднем вычислится меньше, чем за миллисекунду (результатов выполнения своего теста я ждал несколько секунд, а там по паре миллиардов итераций).

железная логика
если бы все мерилось итерациями цикла  smile 


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
MAKCim
Дата 7.11.2007, 23:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



UnrealMan, 
да, если уж на то пошло
давай я докажу, что результаты твоего теста нельзя принять за истину  smile  
Код

time = GetTickCount();
    for (long i=0; i<n; ++i)
    {
        if (typeid(base)!=typeid(Derived))
            return 0; // never return
    }
    t1 = GetTickCount() - time;
    time = GetTickCount();
    for (long i=0; i<n; ++i)
    {
        if (base.GetTypeId()!=&TypeInfo<Derived>::Id)
            return 0; // never return
    }
    t2 = GetTickCount() - time;

циклы большие по количеству итераций, а следовательно почему ты решил, что они будут выполняться атомарно?  smile 
почему в одном из них не может произойти какое-либо событие (будь то прерывание, переключение контекста процесса или еще что-нибудь) а в другом нет?  smile 



--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 7.11.2007, 23:49 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(archimed7592 @  7.11.2007,  23:02 Найти цитируемый пост)
Ты о вычитании уравнений что-нибудь слышал 

Исходя из этой фразы

Цитата(MAKCim @  7.11.2007,  20:49 Найти цитируемый пост)
т. е относительный результат будут тем же

не видно, что имелось в виду решение системы уравнений. Но даже если составить систему уравнений, погрешность будет слишком велика. Ты-то хоть, я надеюсь, это понимаешь?

Цитата(MAKCim @  7.11.2007,  23:09 Найти цитируемый пост)
если бы все мерилось итерациями цикла  

В данном случае именно так и надо мерить. Ведь производительность быстровыполняемых операций важна только тогда, когда эти операции выполняются по многу раз.

Цитата(MAKCim @  7.11.2007,  23:32 Найти цитируемый пост)
циклы большие по количеству итераций, а следовательно почему ты решил, что они будут выполняться атомарно? 

В том-то и дело, что важен средний результат. Погрешность тут, конечно же, возможна, но будет в пределах 10-25 процентов.
PM MAIL   Вверх
MAKCim
Дата 8.11.2007, 00:31 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  7.11.2007,  23:49 Найти цитируемый пост)
не видно, что имелось в виду решение системы уравнений. Но даже если составить систему уравнений, погрешность будет слишком велика. Ты-то хоть, я надеюсь, это понимаешь?

какая погрешность?
я же доходчиво (надеюсь) объяснил, что к чему
время остального кода B постоянно и times это гарантирует если этот остальной код не меняется, а он не меняется
меняются только вот эти части
Код

return static_cast<int>(a1 -> foo() == 2);

и
Код

return static_cast<int>(typeid(C) == typeid(*a1));

время их выполнения равно T1 и T2
общее время, полученное с помощью times равно A1 и A2 соответственно
чтобы получить T1 и T2 мы от A1 и A2 должны отнять B
при B -> 00, пропорции T1 / T2 и A1 / A2 не равны, но ассимптотически приближаются к 1
причем если T1 < T2, то справа, иначе - слева
но относительный результат (быстрее или медленнее) постоянен в не зависимости от B
а т. к B у нас постоянно, то и одного опыта достаточно для того, чтобы опровергнуть или доказать гипотезу

Это сообщение отредактировал(а) MAKCim - 8.11.2007, 00:32


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
MAKCim
Дата 8.11.2007, 00:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



погрешность в моем случае может быть связана с погрешностью получения данных times-ом
эти данные обновляются с частотой системного таймера
в Linux он установлен в 1мс
вычисляйте сами, если хотите, какая может быть погрешность 


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 8.11.2007, 00:53 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  8.11.2007,  00:31 Найти цитируемый пост)
какая погрешность?

И правда, какая погрешность. Система-то уравнений вообще не решаемая smile  archimed7592 сбил с толку smile

Цитата(MAKCim @  8.11.2007,  00:31 Найти цитируемый пост)
чтобы получить T1 и T2 мы от A1 и A2 должны отнять B

И это B нам не известно.

Нам нужно найти T1/T2. Итак, каковы твои действия?

Добавлено @ 00:58
Цитата(MAKCim @  8.11.2007,  00:31 Найти цитируемый пост)
то и одного опыта достаточно для того, чтобы опровергнуть или доказать гипотезу

Так ты ещё и один опыт произвёл smile Мегакруть ©

Это сообщение отредактировал(а) UnrealMan - 8.11.2007, 00:59
PM MAIL   Вверх
MAKCim
Дата 8.11.2007, 10:16 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



UnrealMan, 
Цитата(UnrealMan @  8.11.2007,  00:53 Найти цитируемый пост)
И это B нам не известно.
Нам нужно найти T1/T2. Итак, каковы твои действия?

B нам не нужно!!
T1 / T2 мы заменяем на A1 / A2
при B -> 00, если T1 < T2 ( => A1 < A2), результат неограниченно приближается к 1, но меньше ее
при T1 > T2 ( => A1 > A2) результат приближается к 1, но больше ее
при T1 = T2 ( => A1 = A2) результат 1
на основании одного опыта можно определить соотношение между A1 и A2
и на основании этого сделать вывод о соотношении между T1 и T2
конкретное соотношение не известно в силу неизвестности B, но относительный результат (который нам и нужен) мы получить можем
неужели не понятно?

Добавлено через 1 минуту и 45 секунд
archimed7592, 
вмешайся в спор
кто из нас (я и UnrealMan) тупит

Добавлено через 6 минут и 11 секунд
Цитата(UnrealMan @  8.11.2007,  00:53 Найти цитируемый пост)
Так ты ещё и один опыт произвёл smile Мегакруть ©

а вот это совсем не в тему
хватит флеймить
я тут трачу свое время, распинаюсь, пытаюсь что-то доказать, а в ответ получаю полнейшее нежелание вообще понять о чем говорит собеседник


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
Lazin
Дата 8.11.2007, 10:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3820
Регистрация: 11.12.2006
Где: paranoid oil empi re

Репутация: 41
Всего: 154



Наверное проще разобраться как реализован RTTI на каком либо конкретном компиляторе, как компилятор производит upcast-ы и тд, и сравнить с велосипедом в виде виртуальной ф-ии, сравнением и тд.

PM MAIL Skype GTalk   Вверх
UnrealMan
Дата 8.11.2007, 11:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(MAKCim @  8.11.2007,  10:16 Найти цитируемый пост)
конкретное соотношение не известно в силу неизвестности B, но относительный результат (который нам и нужен) мы получить можем
неужели не понятно?

Ну что я могу сказать? Во-первых, конкретное соотношение было бы интересно узнать. Во-вторых, T1-T2 ты можешь найти, не так ли? И сколько там получается? Время в миллисекундах? Ты всерьёз считаешь, что вот эта несчастная строчка кода вычисляется несколько миллисекунд? Что у тебя там за комп такой?
PM MAIL   Вверх
MAKCim
Дата 8.11.2007, 11:29 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  8.11.2007,  11:17 Найти цитируемый пост)
Во-вторых, T1-T2 ты можешь найти, не так ли? И сколько там получается? Время в миллисекундах?

сам считай, если хочешь
все данные я привел
Цитата(UnrealMan @  8.11.2007,  11:17 Найти цитируемый пост)
Ты всерьёз считаешь, что вот эта несчастная строчка кода вычисляется несколько миллисекунд? Что у тебя там за комп такой? 

 smile 
1. Ты, я так понял, с ассемблером не знаком, так что не делай таких выводов
банальная строчка кода на ЯВУ может разворачиваться в вызов довольно сложной библиотечной процедуры
(что и делается кстати)
2. Я склонен больше доверять стандартной программе, нежели велосипеду (не в обиду сказано)


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
UnrealMan
Дата 8.11.2007, 13:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Мне этот форум нравится всё больше и больше smile Вопросов больше не имею.
PM MAIL   Вверх
MAKCim
Дата 8.11.2007, 14:03 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Воін дZэна
****


Профиль
Группа: Экс. модератор
Сообщений: 5644
Регистрация: 10.12.2005
Где: Менск, РБ

Репутация: 52
Всего: 207



Цитата(UnrealMan @  8.11.2007,  13:30 Найти цитируемый пост)
Мне этот форум нравится всё больше и больше smile Вопросов больше не имею. 

т. е сказать больше нечего?  smile 
ради бога


--------------------
Ах, у елі, ах, у ёлкі, ах, у елі злыя волкі ©

PM MAIL   Вверх
Vyacheslav
Дата 8.11.2007, 20:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Экс. модератор
Сообщений: 2124
Регистрация: 25.3.2002
Где: Москва

Репутация: 9
Всего: 59



Цитата(SaDFromSpb @  7.11.2007,  11:45 Найти цитируемый пост)
Ну во-первых, потому что это когда-то говорил мудрый препод 

Вопрос в том, кто определил , что он мудрый smile.  Поэтому, "во-первых" в расчет не принимаем

Цитата(SaDFromSpb @  7.11.2007,  11:45 Найти цитируемый пост)

  , во-вторых, использование dynamic_cast'а свидетельствует о том, что мы пользуемся какой-то дополнительной функциональностью (RTTI, которую кстати, опциями компилятора можно отключить), чтобы получить истинный (ну или просто более "нижний") интерфейс объекта

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

Цитата(SaDFromSpb @  7.11.2007,  11:45 Найти цитируемый пост)

. Оправданно ли это? Динамик кастом можно пользоваться двумя способами: 1) Приведение, когда ты точно знаешь, какой это класс на самом деле. Но если ты это знаешь, то наверное можно провести такую реорганизацию, чтобы динамик каст не понадобился. 

Дело в том, что если заранее известен класс, то dynamic_cast тут вообще не нужен. Вполне можно обойтись static_cast  .  Так что никакой реорганизации для того, чтобы избавиться от dynamic_cast не понадобится. 


Цитата(SaDFromSpb @  7.11.2007,  11:45 Найти цитируемый пост)

2) Попытка приведения по очереди к нескольким подкласам с отлавливанием ошибок при неправильном приведении (сам так ни разу не пробовал, но вроде можно). - Для С++ это как-то "грязно" =).

То есть исключения для Вас обязательно что-то исключительное? Пусть так. 
Нут так н делайте преобразование без возможной генерации исключений: ограничтесь преобразованием указателей.

Цитата(SaDFromSpb @  7.11.2007,  11:45 Найти цитируемый пост)

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

Смысл этой фразы я не понял :(.
 Но в общем могу сказать, но накладываемые Вами ограничения приводят к  печальному результату: при практическом( не демонстрационном  ) использовании полиморфизма придется 
1)либо перенасыщать интерфейс базового класса( применительно  к к данному  примеру вынести GetTime в базовый класс ), 
2)либо создавать свой механизм опознования ( хотябы с использованием typeid, что кстати не всегда удобно или применимо ) с последующим использованием static_cast, 
3) либо просто отказаться от полиморфизма, потому как обычно в реальных  программах  одной работой со  объектами производных классов  как с базовыми  дело не заканчитвается и рано или поздно от работы с базовым объектом приходится переходить к работе с конкретным объектом конкретного класса. 



--------------------
С уважением, Вячеслав Ермолаев
PM MAIL WWW ICQ   Вверх
archimed7592
Дата 8.11.2007, 20:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(Vyacheslav @  8.11.2007,  20:11 Найти цитируемый пост)
А что в стандарте где есть фразы, дискриминирующие  dynamic_cast?

Не всё, что можно написать в программе будет хорошим ходом с точки зрения проектирования. Стандарт по языку, а не по проектированию.


Цитата(Vyacheslav @  8.11.2007,  20:11 Найти цитируемый пост)
2)либо создавать свой механизм опознования ( хотябы с использованием typeid, что кстати не всегда удобно или применимо ) с последующим использованием static_cast, 

typeid + static_cast == dynamic_cast.




--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
UnrealMan
Дата 8.11.2007, 23:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(archimed7592 @  8.11.2007,  20:27 Найти цитируемый пост)
typeid + static_cast == dynamic_cast

В общем случае это совсем не одно и то же.
PM MAIL   Вверх
Vyacheslav
Дата 9.11.2007, 09:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Экс. модератор
Сообщений: 2124
Регистрация: 25.3.2002
Где: Москва

Репутация: 9
Всего: 59



Цитата(archimed7592 @  8.11.2007,  20:27 Найти цитируемый пост)
typeid + static_cast == dynamic_cast.

В общем то да, но я не часто пользовался typeid и поэтому вопрос: как решить задачу, когда надо преобразовать к не к реальному классу, а к некоемому базовому
A -> B 
   -> C
   -> D ->E
           ->J
          ->H->K
                ->...
 .            
 

Ну и  постановка:  имеется контейнер( дерево),   для  объектов A ( указателей, естественно).  Для всех объектов, которые могут представлены  как объекты класса D выполнить определенную операцию. То есть практически реализовать паттерн Visitor.





--------------------
С уважением, Вячеслав Ермолаев
PM MAIL WWW ICQ   Вверх
archimed7592
Дата 9.11.2007, 11:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Архимед
****


Профиль
Группа: Завсегдатай
Сообщений: 2531
Регистрация: 12.6.2004
Где: Moscow

Репутация: 58
Всего: 93



Цитата(UnrealMan @  8.11.2007,  23:24 Найти цитируемый пост)
В общем случае это совсем не одно и то же. 

В чём разница? 0_о


Цитата(Vyacheslav @  9.11.2007,  09:59 Найти цитируемый пост)
а к некоемому базовому

Для преобразований к базовому касты не нужны вовсе...


--------------------
If you have an apple and I have an apple and we exchange apples then you and I will still each have one apple. But if you have an idea and I have an idea and we exchange these ideas, then each of us will have two ideas.
© George Bernard Shaw
PM Jabber   Вверх
Lazin
Дата 9.11.2007, 12:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3820
Регистрация: 11.12.2006
Где: paranoid oil empi re

Репутация: 41
Всего: 154



Без dynamic_cast нельзя привести указатель от базового класса к потомку при виртуальном наследовании, так как адрес не может быть вычислен во время компиляции, в остальных случаях можно.

PM MAIL Skype GTalk   Вверх
Fazil6
Дата 9.11.2007, 12:24 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1653
Регистрация: 3.5.2006
Где: Минск

Репутация: 35
Всего: 60



Цитата(Lazin @  9.11.2007,  12:00 Найти цитируемый пост)
 в остальных случаях можно.

можно, тока работать будет неправильно smile 
Код

#include <iostream>
struct A
{
    A()
    {
        std::cout << "A constructor\n";
    }
    virtual ~A(){}
};

struct B: public A
{
    B() : x(6), y(4)
    {
        std::cout << "B constructor\n";
    }

    virtual ~B(){}

    
    int y;
    int x;
    void f() {std::cout << x;}
};

struct C : public A
{
    C() : x(1)
    {
        std::cout << "C constructor\n";
    }

    void f1() {std::cout << x;}

    int x;
};

int main()
{
    C c;
    B b;

    C *pc = &c;
    B *pb = &b;

    A *pa1 = pc;
    A *pa2 = pb;

    B *pb2 = (B*)pa1;
    B *pb3 = (B*)pa2;
    
    pb2->f();
    std::cout <<  "\n" ;
    pb3->f();
    std::cout <<  "\n" ;

    return 0;
}

PM MAIL   Вверх
Lazin
Дата 9.11.2007, 12:28 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3820
Регистрация: 11.12.2006
Где: paranoid oil empi re

Репутация: 41
Всего: 154



Цитата(Fazil6 @  9.11.2007,  12:24 Найти цитируемый пост)
можно, тока работать будет неправильно smile 

я знаю, просто в этой теме шла речь об эмуляции rtti средствами языка.
PM MAIL Skype GTalk   Вверх
UnrealMan
Дата 9.11.2007, 13:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 722
Регистрация: 30.3.2006

Репутация: 27
Всего: 32



Цитата(Lazin @  9.11.2007,  12:00 Найти цитируемый пост)
Без dynamic_cast нельзя привести указатель от базового класса к потомку при виртуальном наследовании

Но это ещё не всё. С помощью typeid можно сравнивать типы только most derived-объектов, а dynamic_cast успешно отработает и для промежуточных базовых классов:

Код

#include <iostream>
#include <typeinfo>

struct Base { virtual ~Base() {} };
struct Derived : Base {};
struct MostDerived : Derived {};

int main()
{
    MostDerived mostDerived;
    Base &base = mostDerived;
    if (dynamic_cast<Derived *>(&base))
        std::cout << "object is convertible to Derived" << std::endl;
    if (dynamic_cast<MostDerived *>(&base))
        std::cout << "object is convertible to MostDerived" << std::endl;
    if (typeid(base) == typeid(Derived))
        std::cout << "object is of type Derived" << std::endl;
    if (typeid(base) == typeid(MostDerived))
        std::cout << "object is of type MostDerived" << std::endl;
}

Ещё dynamic_cast способен одним махом произвести такое преобразование:

Код

struct Base { virtual ~Base() {} };
struct Derived1 : Base {};
struct Derived2 : Base {};
struct MostDerived : Derived1, Derived2 {};

int main()
{
    MostDerived mostDerived;
    Derived1 &derived1 = mostDerived;
    Derived2 &derived2 = dynamic_cast<Derived2 &>(derived1);
}

а static_cast пришлось бы применить два раза.
PM MAIL   Вверх
Vyacheslav
Дата 9.11.2007, 15:58 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Экс. модератор
Сообщений: 2124
Регистрация: 25.3.2002
Где: Москва

Репутация: 9
Всего: 59



Цитата(archimed7592 @  9.11.2007,  11:47 Найти цитируемый пост)
Для преобразований к базовому касты не нужны вовсе... 

Вы меня положительно за идиота держите smile
Посмотрите еще раз постановку.
Есть коллекция объектов производных классов, которые выступают как указатели на базовый класс A.  Нужно выполнить определенные операции над объектами только тех классов, которые являются  производными  класса D, то есть над объектами E; J; H; K.

При использовании  dynamic_cast  это решается одной строчкой
Код

 if (D d* = dynamic_cast<D*>(a))
{
    //....
}

При использовании typeid тупо просматривается примерно следущее
Код

 if ( typid(D) == typeid(*a) || typid(E) == typeid(*a) || typid(H) == typeid(*a) || typid(K) == typeid(*a)
{
    D d* = static_cast<D*>(a);
}

Может конечно можно еще как то задействовать type_info::before( const type_info &rhs ) const ,  но проще всетаки dynamic_cast.
И кстати, а разве  typeid для использования динамического типа не использует тот же  RTTI? 




--------------------
С уважением, Вячеслав Ермолаев
PM MAIL WWW ICQ   Вверх
Alek86
Дата 10.11.2007, 11:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
***


Профиль
Группа: Завсегдатай
Сообщений: 1299
Регистрация: 30.1.2007
Где: Киев

Репутация: 21
Всего: 25



оффтоп
хоть кто-то "на моей стороне" smile


--------------------
user posted image    user posted image
PM MAIL   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1353 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.