Здравствуйте, Sinclair, Вы писали:
S>Здравствуйте, x-code, Вы писали: XC>>если кроссплатформенность, то "докомпиляцию" можно было бы выполнить один раз на этапе инсталляции программы, а не делать это каждый раз при запуске. Это же элементарная оптимизация — вынести независящее от цикла вычисление за пределы цикла... S>Это уже сделано, по крайней мере для .Net. RTFM "ngen tool".
За ngen спасибо, для меня это серьезный повод перейти на NET
а как быть с NET'освкими библиотеками (типа WinForms)? Они существуют в виде кода для VM или уже откомпилированные для проца?
XC>>А вся "статистическая" real-time оптимизация, основанная на сборе статистики о наиболее часто вызываемых методах и т.п. — да, ее конечно проще всего реализовать на VM, но совсем не обязательно только на VM. S>Не обязательно. Но VM — это удобная абстракция.
не спорю, более того — то что существуют VM это очень даже хорошо. просто мое ИМХО — не стоит использовать VM везде.
Здравствуйте, x-code, Вы писали:
S>>Это уже сделано, по крайней мере для .Net. RTFM "ngen tool".
XC>За ngen спасибо, для меня это серьезный повод перейти на NET
При этом, как правило, использование ngen-а может привести не только к ускорению работы приложения, но и к его замедлению.
Здравствуйте, Cyberax, Вы писали:
C>FR wrote: >> C>Как? Нам надо уметь как-то в runtime перекомпилировать код. >> Ну Profile Guided Optimization уже давно есть. Он вполне может обходится >> не перекомпиляцией исходников, а переоптимизацией объектников C>PGO может оптимизировать только для некоторых случаев. Горячие точки C>ведь могут мигирировать во время работы программы.
Ну если он будет постоянно и у клиента запущен, то какие проблемы.
>> C>В принципе, если есть доступ к исходникам — можно перекомпилировать из >> C>исходников. Но это все равно будет слегка извращенная VM. >> Если оптимизировать прямо у клиента то исходники не нужны, достаточно >> объектников и правильного линкера. C>А как ты будешь оптимизировать виртуальные вызовы, например?
А какие проблемы, тот же линкер из VC8 уже умеет вынимать из объектника и инлайнить функции, и с виртуальными думаю тот же фокус пройдет. То есть думаю в принципе все вполне реально, вот только нужно ли.
Хотя так любимая тобой низкоуровневая виртуальная машина наверно будет эффективней для такого рода вещей.
FR wrote: > C>PGO может оптимизировать только для некоторых случаев. Горячие точки > C>ведь могут мигирировать во время работы программы. > Ну если он будет постоянно и у клиента запущен, то какие проблемы.
А как ты в ответ на отклик PGO будешь перекомпилировать код (на
клиенте!) и обновлять работающую программу?
> C>А как ты будешь оптимизировать виртуальные вызовы, например? > А какие проблемы, тот же линкер из VC8 уже умеет вынимать из объектника > и инлайнить функции, и с виртуальными думаю тот же фокус пройдет.
Э, нет. При Link Time Code Generation в объектниках помещается
промежуточный код, который при линковке компилируется в машинный. Так
что без VM тоже никуда
Здравствуйте, Cyberax, Вы писали:
C>FR wrote: >> C>PGO может оптимизировать только для некоторых случаев. Горячие точки >> C>ведь могут мигирировать во время работы программы. >> Ну если он будет постоянно и у клиента запущен, то какие проблемы. C>А как ты в ответ на отклик PGO будешь перекомпилировать код (на C>клиенте!) и обновлять работающую программу?
А зачем обновлять работающую программу. Будет копится статистика и при некторых
запусках кое что перекомпилироватся. Да и на ходу при желании можно, у нас же
объектники есть.
>> C>А как ты будешь оптимизировать виртуальные вызовы, например? >> А какие проблемы, тот же линкер из VC8 уже умеет вынимать из объектника >> и инлайнить функции, и с виртуальными думаю тот же фокус пройдет. C>Э, нет. При Link Time Code Generation в объектниках помещается C>промежуточный код, который при линковке компилируется в машинный. Так C>что без VM тоже никуда
Ну так да, но это не полноценная виртуальная машина.
Здравствуйте, x-code, Вы писали:
XC>а как быть с NET'освкими библиотеками (типа WinForms)? Они существуют в виде кода для VM или уже откомпилированные для проца?
Здравствуйте, FR, Вы писали: FR>Нет я ошибся. Они только умеют прямо подставлять вызов виртуальной функции, FR>когда точно известен тип объекта, то есть вызов уже не косвенный.
То-то. А хотспот может
а) убедиться, что в памяти нет классов, перегружающих данный метод, и его можно считать невиртуальным. Ну и, естественно, откатить оптимизацию обратно, когда будет загружен новый класс.
б) даже если есть несколько перегрузок, посчитать, какая из них чаще встречается, и заинлайнить ее. Обрамив, естественно, т.н. guard code, который проверяет — нужный ли класс попался.
И еще много того, что называется Profile-Guided Optimization.
Естественно, PGO не обязательно проводить в динамике (как это делает Java). Информацию о хот спотах можно получить и статически, а затем использовать. Тем не менее, рекомпиляцию с PGO все равно удобнее производить из промежуточного представления.
1.2.0 alpha rev. 655
Уйдемте отсюда, Румата! У вас слишком богатые погреба.
Здравствуйте, Sinclair, Вы писали:
S>Здравствуйте, FR, Вы писали: FR>>Нет я ошибся. Они только умеют прямо подставлять вызов виртуальной функции, FR>>когда точно известен тип объекта, то есть вызов уже не косвенный. S>То-то. А хотспот может S>а) убедиться, что в памяти нет классов, перегружающих данный метод, и его можно считать невиртуальным. Ну и, естественно, откатить оптимизацию обратно, когда будет загружен новый класс. S>б) даже если есть несколько перегрузок, посчитать, какая из них чаще встречается, и заинлайнить ее. Обрамив, естественно, т.н. guard code, который проверяет — нужный ли класс попался.
Кстати такое можно и на C++ замутить.
S>И еще много того, что называется Profile-Guided Optimization.
Ну PGO уже подерживается C++ компиляторами, хотя конечно у них он беднее.
S>Естественно, PGO не обязательно проводить в динамике (как это делает Java). Информацию о хот спотах можно получить и статически, а затем использовать. Тем не менее, рекомпиляцию с PGO все равно удобнее производить из промежуточного представления.
Здравствуйте, FR, Вы писали:
FR>Ну тот же VC8 именно так и поступает.
Ну вот промежуточное представление, скорее всего, и есть код для какой-то "виртуальной машины".
1.2.0 alpha rev. 655
Уйдемте отсюда, Румата! У вас слишком богатые погреба.
Здравствуйте, Геннадий Васильев, Вы писали:
ГВ>Я бы обозначил так: ещё одна цель. Ещё одна в целом ряду целей, для достижения которых разрабатывались ЯП: обучение, символьная обработка, доказательство теорем, системное программирование и т.п.
Не хочу вдаваться в муторные и многословные препирательства, но закономерности сами по себе не имеют цели. Ни в одной науке. Какова, например, цель Закона Всемирного Тяготения или Закона Ома? Да никакая. Человек просто может использовать эти законы на практике. И тут он сам находит цель. Но закономерности не имеют цели.
Мы же в своей статье попытались показать, как указанная закономерность может быть приспособлена для проектирования архитектур, устойчивых к изменениям.
ГВ>Думаю, что само числительное "триста" (или какой-либо его прямой семантический аналог) не появилось бы без предварительного появления системы счисления как таковой. То есть тут налицо впитывание разговорным языком специальной "математической" нотации. Впрочем, повторюсь, что я — не лингвист.
Это обстоятельство опять-таки развенчивает миф о "естественном" языке. Для счета был изобретен язык математики. Поскольку он оказался удобен, он в каком-то трансформированном виде и перекочевал в "естественный" язык. А вот "естественный" язык (изначально) для счета был неудобен.
ГВ>Опять таки, думаю, что дело здесь было в необходимости что-то посчитать. Отсюда и появилась система обозначений чисел и операций над ними.
Вы опять процитировали фразу из моего предыдущего сообщения своими словами. Зачем?
КЛ>>Точно так же и с другими областями человеческой деятельности. Попробуйте-ка написать программу уровня Microsoft Word на естестественном языке. Полагаю, еще та задачка. Не случайно, авторы ряда фундаментальных книг по алгоритмам и структурам данных как только дело доходит до описания алгоритмов, предпочитают псевдокод. А некоторые продвинутые товарищи изобретают даже собственные языки программирования — специально для записи алгоритмов.
ГВ>Вот в этом абзаце что-то логическую связь улавливаю плохо. Да, Word, наверное, трудновато сформулировать на разговорном языке. Но его вполне можно выразить на ассемблерных мнемониках. И кроме того, некорректно упоминать Word в контексте обсуждения мутаций языков програмирования: он появился тогда, когда "культура" обозначений в языках программирования уже достаточно устоялась. А в то время, когда изобретались первые обозначения "mov", "add" и прочие подобные, задачи WYSIWYG-редактора ещё не стояло.
Попробую пояснить еще раз. Вы взяли за основу миф о компьютере, понимающем так называемый "естественный" язык. И высказались в том роде, что это цель, ради которой и были проведены все те преобразования над языками программирования, которые описаны в нашей статье. В качестве доказательства Вы привели 2 факта:
1) Названия мнемоник являются сокращениями английских слов: mov, add, jmp и т.д.
2) В программе на языке высокого уровня можно записать выражение в "математическом" виде: b = a + 1
Не отрицая важности того, что язык программирования должен быть более доступен для человека за счет использования слов из естественного языка, я Вам привел 2 контраргумента:
1) "Математический" язык не является "естественным" языком, поскольку он разрабатывался специально для решения задач счета. Наоборот, т.н. "естественный" очень плохо подходит для счета. Пример я Вам уже приводил выше.
При этом "математический" язык оказался таким успешным, что затем частично перекочевал и в "естественный" язык — Ваш пример про слово "триста".
2) Пример с Microsoft Word'ом я Вам привел для того, чтобы Вы поняли, что даже если компьютер будет понимать "естественный" язык, это никак не поможет в создании подобной программы. "Естественный" язык не только не упростит запись алгоритмов, но еще внесет серьезные проблемы для команды сопровождения, если каждый программист начнет надиктовывать алгоритм на своем диалекте.
Таким образом, "естественность" языка тут совершенно не при чем. Основой для надсистемного перехода (для перехода на новый уровень абстракции) могут быть совершенно разные языки, понятия или системы понятий (==контексты). В одном случае цифры заменили сокращениями "естественных" слов, и получили мнемоники. В другом случае основой послужил язык математики, и программистам стали доступны конструкции вида b = a + 1. В третьем случае основой может оказаться что-то еще, чего еще в помине не существует. И это что-то предстоит еще создать. Так что не нужно зцикливаться на каком-то мифическом "естественном" языке, а лучше поискать подходящие контексты для группирования сущностей. Именно эти контексты и дадут все необходимые термины.
Так в одном из предыдущих обсуждений Вы спросили меня "Что общего между трубкой курительной и трубкой телефонной?" Если помните, я Вам ответил, что для нахождения общности нужно искать контекст. Например, таким контекстом может являться опись имущества. И с точки зрения описи имущества обе трубки — лишь строки в ней.
Здравствуйте, Геннадий Васильев, Вы писали:
ГВ>В чём разбираться? В закономерности, выделенной на основании поверхностного анализа, когда эта поверхностность видна невооружённым глазом? Вам знаком тезис, что любая проблема программирования может быть решена введеним дополнительного уровня абстракции, за исключением проблемы слишком большого количества уровней абстракции? Заметьте, сказано это остаточно давно, чтобы уже стать притчей во языцех. А вы тут пытаетесь нам "продать" этот же рецепт, но под лозунгом ТРИЗ. И кто тут кого обманывает?
Речь идет НЕ только и не столько об уровнях абстракции при решении задач программирования, сколько:
1) о частной, но очень распространенной проектной ошибке, которая называется "проскок системного уровня" и которая приводит к наведенной задаче многофакторности;
2) а также о том, что есть тенденция развития ОТРАСЛИ В ЦЕЛОМ, которая пока развивается "этажами" — Если бы это (на уровне отрасли) было известно давно и стало притчей во языцех, никто бы не считал бы "откровениями" ни ООП (в свое время), ни паттерны проектирования (сейчас).
3) о проектировании "сверху вниз" — да, и это не "новость", между тем, достаточно посмотреть это обсуждение, чтобы понять какой протест это вызывает.
4) о том, что кроме уровней есть "полутона".
5) о том, что — думая над проектом — разработчик понимает его как набор сущностей третьего или четвертого уровня, куда он в процессе работы добавляет сущности уровня 1, 2 и 3. А потом из этих сущностей уровня "1,2,3" он пишет сразу объект уровня 6 (программу), совершая, тем самым, "проскок уровней".
Т.е., о том, что программист, конечно знает "про уровни абстракции", но не отождествляет их с этапами написания программы.
Касательно "много уровней — мало уровней", смотрите статью про "много-мало". Она специально названа "Как вспомнить и так известное", хотя, если Вы скажете, что формулировка противоречий в программировании общепринята — это не будет соответствовать действительности.
Ссылка на материал по ТРИЗ — это ссылка на публикацию 1979 года (не вчерашнюю, мягко говоря), причем указана именно аналогия и написано "сказано по другому поводу".
Ссылки на первоисточники мы делаем — см. список литературы.
Здравствуйте, x-code, Вы писали:
XC>как раз это я понимаю. и знаю что реально методы компилируются в реальный код x86 при первом вызове. Непонятно — зачем? Какие преимущества дает операция "докомпилировать при первом вызове, запомнить в кэше и выполнить" по сравнению с просто "выполнить"? XC>Я не против собственно VM, у них есть масса достоинств, но почему не сделать опцию в компиляторе "генерировать код для VM" и "генерировать код для x86" (а заодно "генерировать код для процессора/VM "X", где X — некоторая архитектура, а для компилятора — просто некоторый плагин)?
Дык в том же дотнете есть NGen который как раз создает образы с бинарным кодом который уже не надо прекомпилировать при запуске.
А приемущество очевидно — прекомпиляция проводится на конкретной машине с кокретными процессором, памятью и т.п. Плюс, потениально, можно использовать информацию от мониторинга исполнения (профилирование, но на конкретной железке).
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, x-code, Вы писали:
XC>За ngen спасибо, для меня это серьезный повод перейти на NET
Поясни, а с чего это для тебя стало поводом?
Открою тебе один сикрет. Скорость выполнения это не поднимает. Это поднимает только скорость загрзуки, и то в большинстве случаев этого не заметить в микроском. Я впервые почувствовал необходимость в пре-помпиляции только когда сатал пользоваться Nemerle. Его компилятор так интенсивно исползует функциональные объекты (которые конвертируются в тучу простеньких классов), что загрузка компилятора занимает очень ощутимое время. С ngen-ом оно практически счезает. Но когда я писл на C#, то ни одна мая программа не требовала ngen-а (точнее время ее загрузки практически не менялось после ngen-а).
XC>а как быть с NET'освкими библиотеками (типа WinForms)? Они существуют в виде кода для VM или уже откомпилированные для проца?
Практически все библиотеки дотнета прекомпилированы.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, Sinclair, Вы писали:
FR>>Нет я ошибся. Они только умеют прямо подставлять вызов виртуальной функции, FR>>когда точно известен тип объекта, то есть вызов уже не косвенный. S>То-то. А хотспот может
Вообще-то в некоторых случаях может. S>а) убедиться, что в памяти нет классов, перегружающих данный метод, и его можно считать невиртуальным. Ну и, естественно, откатить оптимизацию обратно, когда будет загружен новый класс.
Ага. Очень похоже действуют С++-ные компиляторы. Только в рамках ехе-шника.
S>б) даже если есть несколько перегрузок, посчитать, какая из них чаще встречается, и заинлайнить ее. Обрамив, естественно, т.н. guard code, который проверяет — нужный ли класс попался.
Вот толкьо такая проверка приблизительно равна виртуальному вызову. Так что вигрыша не будет или он будет очень не существенным.
Вот в Яве 1.7 обещают эскеп-анализ. Может он позволит выявлять "короткие" объекты и тогда оптимизации можно будет делать более уверенно.
S>И еще много того, что называется Profile-Guided Optimization. S>Естественно, PGO не обязательно проводить в динамике (как это делает Java). Информацию о хот спотах можно получить и статически, а затем использовать. Тем не менее, рекомпиляцию с PGO все равно удобнее производить из промежуточного представления.
Вот только как показывает практика дотнетный код без всех этих выкрутасов обычно работает быстрее. Может тому виной менее качественная работа Сновчников, а может все эти изыски мало что дают на фоне остальных проблем.
Кстати, тут так часто обсуждают избавление от виртуальных вызовов, что можно подумать, что это галавная проблема производительности. Меж тем виртуальные вызовы не видно в микроспом в большинстве случаев. Их можно заметить если с их помощью делаются сложения или сравнения целых, а в ОО-программе их применение просто незаметно.
... << RSDN@Home 1.2.0 alpha rev. 637>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, VladD2, Вы писали:
VD>Кстати, тут так часто обсуждают избавление от виртуальных вызовов, что можно подумать, что это галавная проблема производительности. Меж тем виртуальные вызовы не видно в микроспом в большинстве случаев. Их можно заметить если с их помощью делаются сложения или сравнения целых, а в ОО-программе их применение просто незаметно.
Думаю, что избавление от виртуальных методов позволяет не останавливать на них оптимизацию и, например, инлайнить, а иногда и полностью устранять вызов методов.
... << RSDN@Home 1.2.0 alpha rev. 0>>
Если нам не помогут, то мы тоже никого не пощадим.
Здравствуйте, VladD2, Вы писали:
VD>Здравствуйте, x-code, Вы писали:
XC>>За ngen спасибо, для меня это серьезный повод перейти на NET
VD>Поясни, а с чего это для тебя стало поводом?
я не хочу чтобы функция при первом вызове работала дольше чем при последующих.
хотя, честно сказать, я серьезно C# не занимался, мне просто стало интересно почему пошла такая тенденция перехода к виртуальным машинам.
VladD2 wrote: > Вот толкьо такая проверка приблизительно равна виртуальному вызову. Так > что вигрыша не будет или он будет очень не существенным.
Выигрыш есть достаточно заметный, так как branch instruction очень
эффективно оптимизируется предсказателем переходов. У нас там в
большинстве случаев она займет один-два такта.
> Вот только как показывает практика дотнетный код без всех этих > выкрутасов обычно работает быстрее. Может тому виной менее качественная > работа Сновчников, а может все эти изыски мало что дают на фоне > остальных проблем.
Сильно быстрее он никогда, собственно, и не был. Просто некоторые вещи у
MS были более качественно оптимизированы. Ну и во фреймворке от MS
меньше используется виртуальных вызовов из-за необходимости их явно
указывать.
А Sun JDK 1.6 теперь по некоторым моим тестам работает значительно
быстрее .NET.
> Кстати, тут так часто обсуждают избавление от виртуальных вызовов, что > можно подумать, что это галавная проблема производительности. Меж тем > виртуальные вызовы не видно в микроспом в большинстве случаев. Их можно > заметить если с их помощью делаются сложения или сравнения целых, а в > ОО-программе их применение просто незаметно.
Заметны, очень даже заметны.
А вообще, inlineing (не только виртуальных методов) — это самая
эффективная оптимизация.