Re[37]: плохой язык C++ :)
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 10:54
Оценка:
Здравствуйте, prVovik, Вы писали:

V>Далее, в моем случае библиотека использовала фиксированные небольшой буфер памяти,


Ага. На 8 000 сообщений.

Пойми, что все твои рссуждения о скорости выделения памяти — это чистой воды фобии. Если бы писал свою программу на дотенте, то ты бы и не заметил никаких проблем.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[38]: плохой язык C++ :)
От: igna Россия  
Дата: 22.03.06 11:05
Оценка:
Здравствуйте, VladD2, Вы писали:


VD>Прошу обратить внимание на то, что это ответ на реплику:


VD>А сообщения одного размера? Ой не верю.
>А вдруг? А может это и вовсе одно и то же сообщение выводимое 10000000 раз в секунду, чтобы поиздеваться над сборщиком мусора?


VD>Оппоненты откровенно неразбираются в сути вопроса и всю свою логику строют на основе совбственных фобий и предубеждений.



Понравилось? Я рад. А может это процитированное пару раз сообщение было написано, чтобы поиздеваться не над сборщиком мусора?
Re[39]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 11:05
Оценка:
Здравствуйте, prVovik, Вы писали:

V>Конечно, быстрее будет фиксированный буфер небольшого размера с последовательным доступом.

Не факт.
V>Могут быть сомнения?
Если буфер выпал из кеша процессора то могут..., а ты там еще про своп говорил...

V>Сервер перестанет принимать новые сообщения, пока не разгребет старые. Пользователей "лаганет".

И как часто он лагает?

V>*мечтательно* эх, а была бы память бесконечной, ее бы тогда вообще не надо было бы освобождать

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

Вобще 3 поколения нужны для того чтобы эффективно работать в условиях когда существует большое колличество объектов с коротким временем жизни. Большинство объектов умрет в нулевом поколении. В первое поколение попадают долгоживущие объекты и случайно выжившие короткоживущие объекты(они использовались в момент когда произошла сборка нулевого поколения). К моменту сборки первого поколения вероятность того что кто-то ссылается на короткоживущие объекты практичеки равна нулю. Те во второе поколение попадут только долго живущие объекты.
Таким образом сборка нулевого покаления отрабатывает просто мнгновенно(особенно если учесть то что все в кеше процессора), первое поколение используется как буфер для случайно уцелевших объектов, а во втором поколении сидят объекты с длинным временем жизни... их туда сослали чтобы по ногами не путались.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[41]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 11:15
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Реально и сборка второго поколения не страшна, так как может производиться с помощью Concurrent GC.

Кстати ИМХО лучший вариант для мягкого реалтайма типа игр это собирать нулевое и первое поколение обычным мусорщиком, а второе конкурентным.

VD>И что самое забавное порождающие при этом монстров вроде ФИРА.

Я его на своей машине так и не смог запустить... хотя машина зверь... четвертая квака летает. Может конечно компакт кривой попался...
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[36]: плохой язык C++ :)
От: prVovik Россия  
Дата: 22.03.06 11:15
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Здравствуйте, prVovik, Вы писали:

V>>При чем тут ассемблер и высокоуровневые языки?
VD>При том, что ручное уравление памятью ничем не отличается от ручного управления кодогенерацией.
Хм... Ничего не понял. А что общего между кодогенерацией и алгоритмами управления памятью?

VD>Пойми. И GC и неуправляемые коучи пишут не идеоты.

Не сомневаюсь в этом. Но они и понятия не имеют о МОЕЙ задаче.

VD>И если у меня скоростная характеристика близка к O(1), то хоть в лепешку разбейся но серьезного выигрыша ты неполучишь.

Неужели? А если константа будет час?

VD>Знаешь, как легче всего получить выигрыш от собственной реализации кучи?

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

VD>Просто не задействовать в ней защиту от многопоточного доступу. Блокировки (даже самые легкие) отнимают основное время при выделении памяти.

Ну вот ты и сам сказал, что универсальное средство не всегда оптимально. Именно об этом я и толковал. Точнее о том, что хорошо, когда средство разработки предоставляет возможность удобно реализовать вещи, которые не были предусмотрены создателями данного средства разработки. ТО есть тут имеет место старый спор о том, что лучше: много-много рыбы, или удочка. Я хочу сказать, что на данный вопрос невозможно дать однозначный ответ и очень часто случается, что предпочтительнее иметь удочку, а не рыбу.

VD>В ЖЦ, выделение памяти в них деалется просым инкрементом. И основные затраты тут тоже на блокировку.

Прямо как в том анекдоте про студента, который попал в студенческий ад. Пол года веселился, а потом пришел черт и начал вбивать в зад гвозди.

V>>Это был проект сетевого движка для MMORPG. Приходило 8к сообщений (разного размера) в секунду и управление памятью как раз было узким местом.

VD>Так, все! На этом мы пожалуй закончим. В сумашедший дом я не играю.
Ты о чем?

VD>Читай классику: Оптимизация – ваш злейший враг
Автор(ы): Dr. Joseph M. Newcomer
Дата: 25.06.2005
В этом эссе доктор Ньюкамер делится своим опытом и соображениями по поводу преждевременной, несвоевременной или неактуальной оптимизации, призывая программистов избежать подобных ошибок.

Давай без снизходительного тона, ок? Ты думаешь, что я от нечего делать занялся оптимизацией? Естественно, сначала все было сделано "в лоб", и когда глянули на производительность, пришлось прослезиться. А потом профайлер в зубы и вперед.

VD>Бнин, свой хип для оптимизации 8 000 выделений объектов в секунду, да еще в программе которая по определению не предвявлет особых требований к производительности.

Во-первых, требования к производительности были очень жесткими. Во-вторых, читай выше, не хочу повторяться.
лэт ми спик фром май харт
Re[40]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 11:18
Оценка:
Здравствуйте, igna, Вы писали:

I>Это да. Но то, что на C# можно писать не создавая мусора, не отменяет того, что библиотека .NET Framework иногда создает его там, где это не является необходимым; например StreamReader.ReadLine при каждом вызове возвращает новый String, и в классе StreamReader нет метода читающего в имеющийся StreamBuilder.

По сравнения с чтением с диска...
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[38]: плохой язык C++ :)
От: prVovik Россия  
Дата: 22.03.06 11:19
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Здравствуйте, prVovik, Вы писали:


V>>Далее, в моем случае библиотека использовала фиксированные небольшой буфер памяти,


VD>Ага. На 8 000 сообщений.

Что смешного?
лэт ми спик фром май харт
Re[37]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 11:23
Оценка: +1 :)
Здравствуйте, prVovik, Вы писали:

VD>>Пойми. И GC и неуправляемые коучи пишут не идеоты.

V>Не сомневаюсь в этом. Но они и понятия не имеют о МОЕЙ задаче.
Вот только главный прикол в том что ГЦ как будто специально оптимизировали под твою задачу.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[41]: плохой язык C++ :)
От: igna Россия  
Дата: 22.03.06 11:27
Оценка:
Здравствуйте, WolfHound, Вы писали:


I>>... StreamReader.ReadLine при каждом вызове возвращает новый String, и в классе StreamReader нет метода читающего в имеющийся StreamBuilder.


WH> По сравнения с чтением с диска...



Кто сказал? Почему с диска?
Re[42]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 11:38
Оценка:
Здравствуйте, igna, Вы писали:

I>Кто сказал? Почему с диска?

Ну еще может быть из сети... да еще и через дешифратор с декомпрессором...
Короче ИМХО случаи где можно заметить создание этой строки настолько редки что создатели фреймворка решили с этим не заморачиваться. К тому же если у нас ReadLine то поток текстовый... а текстовые данные в критических к производительности местах обычно не гоняют. Ну не сочетается текст с выжиманием производительности. Ну никак.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[37]: плохой язык C++ :)
От: eao197 Беларусь http://eao197.blogspot.com
Дата: 22.03.06 11:41
Оценка:
Здравствуйте, eao197, Вы писали:

E>Как я понимаю, речь шла не о 8K объектов в секунду, а об обработке 8K сообщений в секунду. Еще не известно, сколько и чего создавалось во время обработки одного сообщения. А обработка 8K сообщений в секунду в сетевом приложении это не кисло.


2VladD2: а минус за что? С чем конкретно ты не согласен?


SObjectizer: <микро>Агентно-ориентированное программирование на C++.
Re[40]: плохой язык C++ :)
От: prVovik Россия  
Дата: 22.03.06 11:42
Оценка: +1
Здравствуйте, WolfHound, Вы писали:

WH>Здравствуйте, prVovik, Вы писали:


V>>Конечно, быстрее будет фиксированный буфер небольшого размера с последовательным доступом.

WH>Не факт.
V>>Могут быть сомнения?
WH>Если буфер выпал из кеша процессора то могут..., а ты там еще про своп говорил...
А ничего, что ГЦ старается "сожрать" как можно больше памяти, она что, типа вся целиком в кеше помещается и никогда не выпадает?
А про своп я говорил, чтобы подчеркнуть, что из всего буфера активно используется только маленькая его часть, которая, кстати, и будет находиться в кеше.

V>>Сервер перестанет принимать новые сообщения, пока не разгребет старые. Пользователей "лаганет".

WH>И как часто он лагает?
А хз
Это уже были не мои проблемы.

V>>*мечтательно* эх, а была бы память бесконечной, ее бы тогда вообще не надо было бы освобождать

WH>Память будет освобождена при сборке первого поколения, а оно собирается гораздо реже чем нулевое и к томц времене с большой вероятностью весь блок станет мусором те будет просто помечен как свободный, а если там и останутся живые объекты то скопировать несколько килобайт для современного железа это вобще не проблема.

WH>Вобще 3 поколения нужны для того чтобы эффективно работать в условиях когда существует большое колличество объектов с коротким временем жизни. Большинство объектов умрет в нулевом поколении. В первое поколение попадают долгоживущие объекты и случайно выжившие короткоживущие объекты(они использовались в момент когда произошла сборка нулевого поколения). К моменту сборки первого поколения вероятность того что кто-то ссылается на короткоживущие объекты практичеки равна нулю. Те во второе поколение попадут только долго живущие объекты.

WH>Таким образом сборка нулевого покаления отрабатывает просто мнгновенно(особенно если учесть то что все в кеше процессора), первое поколение используется как буфер для случайно уцелевших объектов, а во втором поколении сидят объекты с длинным временем жизни... их туда сослали чтобы по ногами не путались.
Обрати внимание. При реализации этой стратегии принималась во внимение некоторая частность о характере управления памятью, а именно, утверждение, что чем раньше был создан объект, тем больше вероятность, что он скоро будет уничтожен. И нетовский ГЦ был создан с ориентировкой именно на эту частность. Да, согласен, что это наиболее распространенная схема управления памятью (кстати к другим ресурсам это уже относится в меньшей степени), и высокая производительность этого ГЦ как раз и обусловлена на заточку под эту схему управления памятью.

Все хорошо, когда программа укладывается в стандартные рамки нетовского ГЦ LIFO (последним создался — первым удалишься — LCFD скорее ), все замечательно работает. Примеры супер-быстрой работы такого ГЦ на схеме использования памятью, на которую он расчитан, неоднократно приводились. Это, лишь, доказывает, что код, занимающийся управлением памятью должен знать о характере ее использования. Но случаи бывают разные. Вот помню, как Сергей Губанов как-то приводил пример, в котором "убогий" обероновский ГЦ "рвал" дотнетовский. А все потому, что схемы использования памяти была не LIFO (LCFD), а FIFO (FCFD). А вот если бы дотнетовский гц был ориентированн на последнюю схему, все было бы иначе . Это я к тому, что не бывает серебрянных пуль, которые хорошо работают во всех случаях. Для каждого супостата нужен свой снаряд
лэт ми спик фром май харт
Re[41]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 12:24
Оценка: +1
Здравствуйте, prVovik, Вы писали:

V>А ничего, что ГЦ старается "сожрать" как можно больше памяти, она что, типа вся целиком в кеше помещается и никогда не выпадает?

Размеры нулевого и первого поколений фиксированы. Растет второе поколение в котором сидят долгоживущие объекты.
Сообщения из твоей задачи туда не попадут.
V>А про своп я говорил, чтобы подчеркнуть, что из всего буфера активно используется только маленькая его часть, которая, кстати, и будет находиться в кеше.
Те делаем вывод что сервер очень оперативно выгребал сообщения. А заторы были очень редки. Так?

V>Обрати внимание. При реализации этой стратегии принималась во внимение некоторая частность о характере управления памятью, а именно, утверждение, что чем раньше был создан объект, тем больше вероятность, что он скоро будет уничтожен. И нетовский ГЦ был создан с ориентировкой именно на эту частность. Да, согласен, что это наиболее распространенная схема управления памятью (кстати к другим ресурсам это уже относится в меньшей степени), и высокая производительность этого ГЦ как раз и обусловлена на заточку под эту схему управления памятью.

Причем твоя задаче прекрасно в эту схему укладывается. А другими ресурсами в .NET релят ручками. Причем лично мне using + IDisposible хватало всегда.

V>Все хорошо, когда программа укладывается в стандартные рамки нетовского ГЦ LIFO (последним создался — первым удалишься — LCFD скорее ), все замечательно работает. Примеры супер-быстрой работы такого ГЦ на схеме использования памятью, на которую он расчитан, неоднократно приводились. Это, лишь, доказывает, что код, занимающийся управлением памятью должен знать о характере ее использования. Но случаи бывают разные. Вот помню, как Сергей Губанов как-то приводил пример, в котором "убогий" обероновский ГЦ "рвал" дотнетовский. А все потому, что схемы использования памяти была не LIFO (LCFD), а FIFO (FCFD).

Ссылку пожалуйста. Чтото мне мерещится что когда к этому тесту добавили 1000000 вечно живущих объектов (те создали болие или мение реальные условия) оберон просто умер.
Короче не работающая программа можер работать сколь угодно быстро...
V>А вот если бы дотнетовский гц был ориентированн на последнюю схему, все было бы иначе . Это я к тому, что не бывает серебрянных пуль, которые хорошо работают во всех случаях. Для каждого супостата нужен свой снаряд
Бывают посоребренные пули которые хорошо работают в подавляющем большенстве случаев. И для твоего супостата эти пули прекрасно подходят.
Единственный случай когда я отказался от услуг ГЦ в .NET это был бинарный дифф для того чтобы резать на куски бэкап быза RSDN'а. Но там сценарий работы был таким: В начале работы создать несколько миллионов одинаковых объектов, а в конце работы их все удалить. Для этого я воспользовался массивом value типов.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[42]: плохой язык C++ :)
От: prVovik Россия  
Дата: 22.03.06 12:43
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>Те делаем вывод что сервер очень оперативно выгребал сообщения. А заторы были очень редки. Так?

Так, но не забывай, что само по себе время жизни объекта мало что значит. Важно время жизни относительно других объектов. Я не знаю, что именно делал сервер во время обработки каждого сообщения (а делать он мог много чего ), но факт есть факт: сообщения жили по принципу первое создалось, первое удалилось.
лэт ми спик фром май харт
Re[42]: плохой язык C++ :)
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 13:02
Оценка:
Здравствуйте, igna, Вы писали:

I>Может быть, но было так: Пытаюсь сохранить новую запись, нет места. Удаляю некоторые ненужные записи и пытаюсь сохранить еще раз. Телефон "зависает" секунд на 10, потом сохраняет запись. Наблюдал такое поведение несколько раз. Siemens M55.


Siemens M55 вроде как на Symbian OS живет. И телефонная книга у него не на Яве значит.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[37]: плохой язык C++ :)
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 13:02
Оценка:
Здравствуйте, prVovik, Вы писали:

V>По поводу большенства мертвых объектов. Доставала объекты оснавная программа (сервер), а не сетевая библиотека. И когда сервер соизволит достать очередное сообщение — это только серверу известно, и сколько поколений переживут сообщения в буффере тоже не понятно. Далее, подумай про объемы: 8к сообщений в секунду, каждое из которых в среднем по 4 килобайта. Получаем 32 мегабайта в секунду. Некислая я скажу нагрузка на ГЦ будет — дефрагментация получится очень "вкусной" операцией


Ну ты заливаешь! Ты прежде чем токое нести узнал бы какова средняя пропускная способность у 100 мегабитной сети. Я тебе как краевед скажу, что где-то оголо 10 мег в секунду.

На вашей игрушке можно смело писать звучные лозунги вроде:

Мы работаем на будущее!!!... Минимальные требования для сетевой игры Gigabit Ethernet!


А вот для ЖЦ это тем не менее вообще не работа. Вот простенький тест:
using System;
using System.Collections.Generic;
using System.Diagnostics;

class Program
{
    static void Main()
    {
        Stopwatch timer = Stopwatch.StartNew();
        List<char[]> list = new List<char[]>(100);

        for (int i = 0; i < 8000; i++)
        {
            list.Add(new char[4 * 1024]);

            if (i % 100 == 0)
                list.Clear();
        }

        Console.WriteLine(timer.Elapsed);
        for (int i = 0; i <= GC.MaxGeneration; i++)
            Console.WriteLine("Количество сборок в поколнии {0}: {1}", i, GC.CollectionCount(i));
    }
}

Вто что получается на маей машине:
00:00:00.0547748
Количество сборок в поколнии 0: 17
Количество сборок в поколнии 1: 6
Количество сборок в поколнии 2: 0


На этом хочу закончить эту позновательную беседу. Дела, знаете ли, ждут. Фэнтези определенно не мой любимый жанр.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[43]: плохой язык C++ :)
От: WolfHound  
Дата: 22.03.06 13:04
Оценка:
Здравствуйте, prVovik, Вы писали:

V>Так, но не забывай, что само по себе время жизни объекта мало что значит. Важно время жизни относительно других объектов. Я не знаю, что именно делал сервер во время обработки каждого сообщения (а делать он мог много чего ), но факт есть факт: сообщения жили по принципу первое создалось, первое удалилось.

Ну не верю я в что эти объекты попадут дальше первого поколения. И как следствие не будет просадки по производительности.
... << RSDN@Home 1.1.4 beta 6a rev. 436>>
Пусть это будет просто:
просто, как только можно,
но не проще.
(C) А. Эйнштейн
Re[43]: плохой язык C++ :)
От: igna Россия  
Дата: 22.03.06 13:17
Оценка:
Здравствуйте, VladD2, Вы писали:

VD>Siemens M55 вроде как на Symbian OS живет. И телефонная книга у него не на Яве значит.



GC на C++ значит...
Re[39]: плохой язык C++ :)
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 13:22
Оценка:
Здравствуйте, prVovik, Вы писали:

VD>>Ага. На 8 000 сообщений.

V>Что смешного?

"фиксированные небольшой буфер памяти" в количестве 8000, да еще и с размером по 4 К — это 32 метра! И это при том, что сообщения-то идут последовательно.

Развернутый ответ здесь:
Re[37]: плохой язык C++ :)
Автор: VladD2
Дата: 22.03.06
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Re[42]: плохой язык C++ :)
От: VladD2 Российская Империя www.nemerle.org
Дата: 22.03.06 13:22
Оценка:
Здравствуйте, WolfHound, Вы писали:

WH>Кстати ИМХО лучший вариант для мягкого реалтайма типа игр это собирать нулевое и первое поколение обычным мусорщиком, а второе конкурентным.


Так и делается. Вообще-то я об этом в статье написал (из #5 2005). Тебе как члену команды она доступна. Так что можешь почитать. Там об этом как раз и рассказывается.

VD>>И что самое забавное порождающие при этом монстров вроде ФИРА.

WH>Я его на своей машине так и не смог запустить... хотя машина зверь...

Я на домашней запустил. Там 6800 GT с 128 метрами.
Правда пришлось час провести в их тесте (слава богу хоть его сделали) и выяснить что нужно отключить. Основное что пришлось отключиь — это мягкие тени.

WH>четвертая квака летает. Может конечно компакт кривой попался...


4 Квака у меня летает и на машине с ATI 9800 Pro. Причем мягкие тени там не хуже ФИРА.

Короче, в реальном мире релят грамотные специалисты, прямые руки и тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты, тесты.

... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.