В .NET 4.5 новый фоновый сборщик мусора, с ним тоже все плохо?
Не уверен, но похоже, эта часть комментария была адресована мне. Мы перепробовали все возможные настройки GC, которые только есть. Были даже попытки оценивать Memory Pressure и вручную вызывать GC заблаговременно, пока не стало совсем плохо. Ничего не помогало. Ситуацию спас банальный переход на x64 (ещё до RyuJIT). В x86, какой режим сборщика ни включай, всё-равно есть вероятность схватить stop-the-world сборку. Правда, в .NET 4.5 это действительно происходило реже.
Так и есть, конечно. Клиент — на C#, сервер — на Java с подтюненым GC. Клиент раз в секунду отправляет хартбиты, и при потере хотя бы двух хартбитов сервер отменяет все ордера — это специальная защита от зависших на рынке «ничейных» ордеров. Так вот, когда трейдер открывает тысячи инструментов, по каждому из которых тикает маркет-дата, нагрузка на UI такая, что GC иногда не справляется. Ещё раз уточню: да, наверно проблема в неправильной архитектуре и чрезмерном количестве аллокаций. Но то, что GC в .NET-е может стопить весь процесс на 4 секунды, — это неприятно.
Вот эти две фразы выносят мой мозг:
WPF — де-факто наиболее популярная технология для UI в свере банкинга.
Если с самого начала при построении архитектуры грамотно продумать менеджмент памяти, таких проблем не возникает. Но проект старый, и в нём есть множество наслоений функционала, поэтому и возникают подобные проблемы с GC. Универсального решения, увы, нет. Надо профилировать и находить узкие места.
В моём конкретном случае зависание приложения больше чем на 2 секунды было критичным. Мы потратили уйму времени на профилирование и оптимизации, но в результате пришли к выводу, что проще искусственно ограничить возможности системы. Трейдеры хотят видеть на мониторе (вернее, на 5-10 мониторах) по 50 окон, в каждом из которых будет открыто по несколько сотен инструментов с данными, обновляющимися по 10 раз в секунду. Это, если и реализуемо, то на чистом Ассемблере.
Про будущее: как это ни странно, видел пару экспериментальных проектов, написанных под Awesomium (поделка, выросшая из Chromium), где за доступ к данным отвечает C#-код, а за отображение — чистый JS). Не знаю, может быть, и правда будущее за этим.
На сегодняшний день WPF — де-факто наиболее популярная технология для UI в свере банкинга. Я не могу сказать, хорошо это или плохо, но так оно есть, и не мне менять правила. А что бы Вы предложили взамен?
На сколько я понимаю, freeze UI происходит из-за перекомпиляции xaml-файлов во всём солюшне на каждый чих, даже при переключении между табами. Это нужно для корректной работы IntelliSense. Если проект большой, VS будет тормозить. Вроде бы, когда-то давно на коннекте был заведен баг, и его обещали пофиксить, но не помню в какой версии. В последнее время я с ним не сталкивался.
Ну тогда я, как юзер, с Вами не соглашусь. Сейчас я, в основном, использую VS, но когда нужно что-то написать на Java, использую IDEA, и это как глоток свежего воздуха — всё буквально летает. Ваше субъективное восприятие против моего — это я и называю «ни о чём». Нужны объективные тесты производительности.
Про VS + R# — да, есть проблемы, о которых разработчики в JetBrains не скрывают. Но этому есть объективные причины, о которых и говорится в данном интервью. Roslyn построен на immutable-структурах данных, которые дают огромный memory footprint, с которым GC не справляется. В проекте, над которым я сейчас работаю (UI, WPF), stop-the-world GC, порой, работает больше, чем 4 секунды, из-за чего сервер теряет хартбиты, а трейдеры — ордера на сотни тысяч долларов. Из-за этого мы тратим огромное количество времени на оптимизацию расхода памяти. В Java я ни разу не видел FullGC больше секунды.
А мне наоборот понравилось. Если не вдаваться в финансовый вопрос (Мне не особо интересно кто хочет бабла, а кто не хочет. Все хотят.), видно, что менеджмент в JetBrains весьма компетентен в технической части.
По поводу людей, которые что-то делают — не совсем понял. Вы считаете, что программисты, которые написали R#, делают больше, чем руководитель отдела разработки?
> студия 2013 или 2015 работают гораздо шутрее чем идея (24гига озу, ssd, corei5 2500k разогнан до 4.3), net работает быстрее как на десктопе (wpf) так и на серваке asp.net mvc.
Вот это высказывание «ни о чём», как Вы выразились. Сможете доказать?
Надеюсь, когда-нибудь эта консоль сможет подключаться к отладочной сессии приложения с захватом всех текущих объектов при срабатывании break points. Тогда ей и правда цены не будет. А пока я, честно говоря, на могу найти ей применение.
И как архитектурный дизайн, я бы предложил что-нибудь типа stateless-класса StateChecker, который должен единожды инициализироваться правилами проверки состояния. Его можно было бы инстанциировать в нужных местах кода или по аналогии с IEqualityComparer<T> иметь статические синглтоны вроде EqualityComparer.Default для стандартных ситуаций. Но тогда вопрос — чем это отличается, собственно, от IEqualityComparer<T>? Если в нужных местах можно игнорировать какое-то свойство объекта, пожалуйста — напиши свой компаратор, сравнивающий всё, кроме этого свойства.
На сколько я понял, метод «IsInSameState» — это что-то вроде расширенного Equals.
Объект может иметь различный смысл в разных ситуациях. На пальцах, скажем, есть объект
Старушка = new Человек {Паспорт = «4606 456356645» Возраст = 88, Пол = Женский, ОтношениеККурению = СмолитКакПаровоз}
Есть сервисы IПенсионныйФонд и IОбществоПоБорьбеСРаком
Для сервиса IПенсионныйФонд не так уж важно, сколько лет стукнуло бабуле. Паспорт совпадает — значит, она и есть.
Для IОбществоПоБорьбеСРаком паспорт вообще не важен, зато Возраст — критерий для сравнения.
В общем, что я хотел сказать: нельзя State задавать атрибутами. Для разных ситуаций состояние можно интерпретировать по-разному. Я не знаю, с какого языка Вы почерпнули сей паттерн, но мне кажется, данный подход (с атрибутами, как Вы предложили), там долго не продержится.
А вообще, наверняка кто-то сталкивался с подобным, надо только поискать.
Я понимаю. Но когда в C# будут реализованы record типы, можно будет допилить и сборщик мусора. Это я к тому, что вы выше писали про синтаксический сахар. С одной стороны, да, сахар, но с другой стороны, из этого сахара в будущем может быть извлечена серьезная польза для GC.
А как быть с конвертерами при такой записи? И есть ли в планах задача по переходу от XAML на что-то более читаемое? Эдакий Razor для WPF? Ну, или хотя бы поддержка простейших операций типа сложения и тернарного оператора в биндингах? Это, по-моему, один из главных косяков WPF-а. (У меня пока не было времени детально ознакомиться с проектом. Если что-то уже реализовано, замечательно!)
Как?! Как такое может дойти до релиза? Я не стал репортить о проблеме, в полной уверенности, что это очевидный баг, который скоро найдут. Но как бы не так:
Не уверен, но похоже, эта часть комментария была адресована мне. Мы перепробовали все возможные настройки GC, которые только есть. Были даже попытки оценивать Memory Pressure и вручную вызывать GC заблаговременно, пока не стало совсем плохо. Ничего не помогало. Ситуацию спас банальный переход на x64 (ещё до RyuJIT). В x86, какой режим сборщика ни включай, всё-равно есть вероятность схватить stop-the-world сборку. Правда, в .NET 4.5 это действительно происходило реже.
Ну вот, Вы сами ниже подтверждаете, что
В моём конкретном случае зависание приложения больше чем на 2 секунды было критичным. Мы потратили уйму времени на профилирование и оптимизации, но в результате пришли к выводу, что проще искусственно ограничить возможности системы. Трейдеры хотят видеть на мониторе (вернее, на 5-10 мониторах) по 50 окон, в каждом из которых будет открыто по несколько сотен инструментов с данными, обновляющимися по 10 раз в секунду. Это, если и реализуемо, то на чистом Ассемблере.
Про будущее: как это ни странно, видел пару экспериментальных проектов, написанных под Awesomium (поделка, выросшая из Chromium), где за доступ к данным отвечает C#-код, а за отображение — чистый JS). Не знаю, может быть, и правда будущее за этим.
Про VS + R# — да, есть проблемы, о которых разработчики в JetBrains не скрывают. Но этому есть объективные причины, о которых и говорится в данном интервью. Roslyn построен на immutable-структурах данных, которые дают огромный memory footprint, с которым GC не справляется. В проекте, над которым я сейчас работаю (UI, WPF), stop-the-world GC, порой, работает больше, чем 4 секунды, из-за чего сервер теряет хартбиты, а трейдеры — ордера на сотни тысяч долларов. Из-за этого мы тратим огромное количество времени на оптимизацию расхода памяти. В Java я ни разу не видел FullGC больше секунды.
По поводу людей, которые что-то делают — не совсем понял. Вы считаете, что программисты, которые написали R#, делают больше, чем руководитель отдела разработки?
Вот это высказывание «ни о чём», как Вы выразились. Сможете доказать?
Объект может иметь различный смысл в разных ситуациях. На пальцах, скажем, есть объект
Старушка = new Человек {Паспорт = «4606 456356645» Возраст = 88, Пол = Женский, ОтношениеККурению = СмолитКакПаровоз}
Есть сервисы IПенсионныйФонд и IОбществоПоБорьбеСРаком
Для сервиса IПенсионныйФонд не так уж важно, сколько лет стукнуло бабуле. Паспорт совпадает — значит, она и есть.
Для IОбществоПоБорьбеСРаком паспорт вообще не важен, зато Возраст — критерий для сравнения.
В общем, что я хотел сказать: нельзя State задавать атрибутами. Для разных ситуаций состояние можно интерпретировать по-разному. Я не знаю, с какого языка Вы почерпнули сей паттерн, но мне кажется, данный подход (с атрибутами, как Вы предложили), там долго не продержится.
А вообще, наверняка кто-то сталкивался с подобным, надо только поискать.