LINUX.ORG.RU

Производительность C++

 ,


7

13

Как насчёт производительности у C++ по сравнению с C? Мои предположения на текущий момент:

1) Код, не использующий возможности C++ (то есть по сути plain C), скомпилированный C++ компилятором будет иметь абсолютно ту же производительность, что и код на С.

2) Исключения и dynamic_cast медленные. Если нам важна производительность, лучше их не использовать.

3) Класс без виртуальных методов, должен быть по производительности эквивалентен сишной структуре и функциям, обрабатывающим её. Не считая копирования. Нужно везде, где можно использовать передачу по указателю или ссылке (собственно, если в Си делать memmove при передаче структуры в качестве аргумента, то это вызовет примерно такой же оверхед, как дефолтный конструктор копирования С++. Верно?).

4) Класс с виртуальными методами полностью аналогичен пункту 3, но при вызове виртуальных методов добавляется небольшой оверхед. Сишный эквивалент obj->vtable->func(obj, ...). Если сравнивать с plain C кодом, реализующим ООП в той же манере (каждая структура-объект имеет поле, указывающее на структуру, содержащую адреса функций работы с ней), то оверхеда по сравнению с plain C не должно быть.

5) При использовании атрибута класса final (если компилятор поддерживает соответствующий стандарт) даже при наличии виртуальных методов в нём, их вызов будет превращаться в прямые вызовы функций вместо обращения к vtable, если переменная имеет соответствующий тип, а не указатель/ссылка на его предка (который не final).

6) Шаблоны могут привести к разбуханию кода. Впрочем, #define-ы и inline-функции в C++ могут устроить то же самое. Вопрос: будет ли использование шаблона с одинаковыми параметрами создавать 2 копии реализации или же всё-таки компилятор догадается сделать её лишь один раз. А если шаблон используется с одинаковыми параметрами в нескольких объектных файлах? Будет ли реализация расшариваться между ними или у каждого своя?

7) Что насчёт inline-методов класса? (те, которые описываются прямо в момент определения самого класса, внутри блока class). Может ли их реализация расшариваться между модулями или в каждом будет своя копия (допустим, метод слишком длинный, чтобы инлайнится в момент вызова)?

Я не претендую на правоту, какие-то утверждения могут быть ложными. Хотел бы узнать, как обстоят дела на самом деле. А также какие подводные камни я ещё не знаю. Разумеется, речь идёт о последних версиях gcc/clang с включённой оптимизацией не ниже -O2.

★★★★★

Последнее исправление: KivApple (всего исправлений: 1)
Ответ на: комментарий от anonymous

Не понял, а при чем тут возврат строки тогда? Нужно возвращать код ошибки тогда, а не строку.

Ok. Пусть будет код возврата.

Как затем получить текстовое описание ошибки? Например, что в такой-то строке нет закрывающей фигурной скобки, а открывающая была на такой-то строке.

Что за быдлокод?

Покажите лучше.

eao197 ★★★★★
()
Последнее исправление: eao197 (всего исправлений: 1)
Ответ на: комментарий от anonymous

Ну прям образец ведения аргументированной дискуссии.

По фактам того, что я здесь говорил претензии есть?

eao197 ★★★★★
()
Ответ на: комментарий от eao197

Чот вы тут сильно дофига уже с этим анонимным смайликом трете. не надоело кормить?

Кста по возврату. У нас был Result<T, E> в качестве результата функций API задолго до того, как появился раст.

anonymous
()
Ответ на: комментарий от anonymous

У нас был Result<T, E> в качестве результата функций API задолго до того, как появился раст.

Кто в данном случае «мы» - Haskell, Scala?

tailgunner ★★★★★
()
Ответ на: комментарий от anonymous

Чот вы тут сильно дофига уже с этим анонимным смайликом трете. не надоело кормить?

А я не для него пишу. Смайлик высказывает обычные бредни и мифы о C++. Поскольку с C++ сейчас знакомо очень мало разработчиков, то многие на такие мифы ведутся. Что не есть хорошо, поэтому такие мифы нужно развенчивать.

eao197 ★★★★★
()
Ответ на: комментарий от tailgunner

Ну смотри, все функции, кидающие исключения, и все функции, вызывающие функции, кидающие исключения, неявно получают тип Result<T, Error>, а дальше как по нотам: return и throw тупо упаковывают в монаду, ? дает bind, ! распаковывает или прокидывает ошибку на верхний уровень, ?? распаковывает или лениво отдает указанное вторым аргументом значение, catch поддерживает динамическую диспетчеризацию. То есть ты можешь использовать все те же try, catch и throw, но под капотом они будут реализованы через sum type. По факту это абсолютно те же исключения.

mix_mix ★★★★★
()
Ответ на: комментарий от anonymous

Кста по возврату. У нас был Result<T, E> в качестве результата функций API задолго до того, как появился раст.

По накладным расходам Result<int, string>, который можно было бы применить в библиотеке вроде picojson, будет ничуть не лучше возврата просто string-а.

Так что возврат просто string плох прежде всего тем, что нет возможности классифицировать ошибку (например, отличить отсутствие закрывающей фигурной скобки от неверного формата записи целого числа). Но во многих сценариях использования json-а это и не нужно: либо json парсится успешно, либо нет. И если нет, достаточно залогировать текстовое описание.

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

eao197 ★★★★★
()
Ответ на: комментарий от tailgunner

Да особо не напрягало. там строго все было. E - наследники от определенного класса (EBase; проверялось при компиляции), если собиралось с исключениями, то EBase был наследником от exception и мог быть кинут. Сам Result имел оператор bool и легко проверялся if( r ) { ... }.

anonymous
()
Ответ на: комментарий от anonymous

а аноним не из ебурга ? стиль мышление похож на одного кадра

anonymous
()
Ответ на: комментарий от mix_mix

Ну смотри, все функции, кидающие исключения, и все функции, вызывающие функции, кидающие исключения, неявно получают тип Result<T, Error>

Это проходит только как аналогия. Когда надо объяснить исключения в терминах кодов возврата.

По факту это абсолютно те же исключения.

Т.е. общего - аналогия. Тогда окей.

tailgunner ★★★★★
()
Ответ на: комментарий от eao197

Пусть будет код возврата.

Но его там нет.

Как затем получить текстовое описание ошибки?

Ну это уже вопрос к разработчикам библиотеки. Либо возвращать sum type, либо делать как здесь:

https://developer.gnome.org/json-glib/stable/JsonParser.html

anonymous
()
Ответ на: комментарий от anonymous

E - наследники от определенного класса (EBase; проверялось при компиляции)

Экземпляр передавался через указатель?

tailgunner ★★★★★
()
Ответ на: комментарий от eao197

Не сразу, по фактам продемонстрированного вами дебилизма.

Не нужно так сильно переживать по поводу фактов неумолимого сокращения адекватного сообщества цепепе :-) Это мелочи жизни :-)

Ваше предложение давно было понято. Но вы не ответили, что нужно делать в ситуации, когда a) нужно оставаться в рамках C++ и b) использовать исключение нельзя.

Это такой же абсурд, как «что нужно делать, когда хочется морковки, а кроме кактусов ничего нет :-) Лол :-)

Может удивите меня и таки ответите?

Вырастить морковку, если хочется морковки, не кушать кактус :-)

Ануткать, объясните публике, в чем состоит стиль C++14 или, хотя бы, C++98?

Ну как в чём? :-) Генерировать исключение при возникновении ошибки, как учил великий Страуструп и все эксперты C++ мирового уровня :-)

anonymous
()
Ответ на: комментарий от eao197

По фактам того

Да ты как-то фактов-то особо никаких не привел. Все, что я увидел, прочитав тред, это ``дебил, школьник, лень объяснять, никто не пользуется си, вы все тупые, разрабатывать на плюсах дешевле, я сказал!".

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

anonymous
()
Ответ на: комментарий от eao197

А я не для него пишу. Смайлик высказывает обычные бредни и мифы о C++. Поскольку с C++ сейчас знакомо очень мало разработчиков, то многие на такие мифы ведутся. Что не есть хорошо, поэтому такие мифы нужно развенчивать.

Ну какие бредни смайлик высказал? :-) Он всего лишь намекает, что язык должен использоваться либо полностью, либо никак :-) Если исключения портят малину, нужно отказываться от C++ в пользу того же C, а не кушать кактусы :-) Просто же всё у нас с этим :-)

anonymous
()
Ответ на: комментарий от tailgunner

Ошибки - да.

А результат трейтами определялся. Через указатели (большие матрицы например) или прям в теле (если там один float).

anonymous
()
Ответ на: комментарий от anonymous

Ну это уже вопрос к разработчикам библиотеки.

Разработчики уже нашли ответ на этот вопрос. Мне интересно, что лично вы бы предложили на их месте.

eao197 ★★★★★
()
Ответ на: комментарий от anonymous

Ну какие бредни смайлик высказал? :-)

Ну вот например:

улыбчивый_дурачок> язык должен использоваться либо полностью, либо никак

улыбчивый_дурачок> Если исключения портят малину, нужно отказываться от C++ в пользу того же C,

tailgunner ★★★★★
()
Последнее исправление: tailgunner (всего исправлений: 1)
Ответ на: комментарий от anonymous

Все, что я увидел, прочитав тред, это ``дебил, школьник, лень объяснять, никто не пользуется си, вы все тупые, разрабатывать на плюсах дешевле, я сказал!".

А теперь попробуйте ответить за свои слова и показать, где я говорил, например, про «никто не пользуется си».

Ну и как можно назвать человека, который не видит в стандарте явного указания того, что спецификатор throw deprecated да еще и кичится этим?

eao197 ★★★★★
()
Ответ на: комментарий от tailgunner

Ты лишь цитируешь некоего смайлика :-) Зачем лишний раз гонять трафик, если его высказывания итак все увидели :-) Почему ты никогда не обосновываешь свои заявления, как и в этом случае, ограничиваясь лишь бессмысленным цитированием? :-)

anonymous
()
Ответ на: комментарий от anonymous

Зачем лишний раз гонять трафик, если его высказывания итак все увидели

Ты задал вопрос - я на него ответил.

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

Когда я говорю с разумным человеком - обосновываю. Но ты не являешься разумным человеком.

tailgunner ★★★★★
()
Ответ на: комментарий от eao197

Ну и как можно назвать человека, который не видит в стандарте явного указания того, что спецификатор throw deprecated да еще и кичится этим?

Ну так возникает вопрос, что, неужто человека, не увидевшего в 1300 страничном стандарте строчку про deprecated, называть дебилом может лишь абсолютный чемпион по C++? :-)

anonymous
()
Ответ на: комментарий от eao197

Ну вот разработчики glib дошли умом до сам типа, инкапсулирующего область ошибки, код и строку. А вот разработчики этой либы — нет. И вот так всегда с крестами, каждый городит свой огород. Даже у си с этим на порядок лучше, там либо errno, либо анклав гнома. В крестах никакой консистентности, потому пользоваться можно только каким-нибудь фреймворком, вроде культей/глиба, где все есть, либо пытаться связать вот это вот все воедино.

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

anonymous
()
Ответ на: комментарий от tailgunner

Когда я говорю с разумным человеком - обосновываю. Но ты не являешься разумным человеком.

Являюсь, ведь моему разуму не ведомо возвращать ошибку в виде std::string и функции синтаксического разбора, в отличии от :-)

anonymous
()
Ответ на: комментарий от eao197

throw deprecated

Это че, теперь исключения нельзя выбрасывать? Интересно, и какой ныне идиоматический способ сообщения об ошибке в крестах? А потом он говорит, что никто с крестами не знаком. Авторы бы хоть определились с каким-то образом языка, что есть кресты, как не прикрученный к сишке набор разрозненных фич, еще и объявляющихся устаревшими.

anonymous
()
Ответ на: комментарий от anonymous

Ну вот разработчики glib дошли умом до сам типа, инкапсулирующего область ошибки, код и строку. А вот разработчики этой либы — нет.

Это крошечная header-only либа. Отдельный тип ошибок ей излишен.

tailgunner ★★★★★
()
Ответ на: комментарий от anonymous

Генерировать исключение при возникновении ошибки, как учил великий Страуструп и все эксперты C++ мирового уровня

Боюсь, вы, как обычно, смотрели в книгу, а видели лишь то, что хотели увидеть.

По поводу отказа от C++ и программирования на C. Рекомендую почитать о разработке софта для управления двигателями на C++. Там embedded, но C++ с шаблонами использовался для того, чтобы упростить разработку и повысить надежность кода. Например, вот здесь это описывается: http://www.stroustrup.com/abstraction-and-machine.pdf

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

eao197 ★★★★★
()
Ответ на: комментарий от tailgunner

Класс с тремя полями/простенький шаблон в либе из наверное более тысячи строк — излишен? Какое-то дешевое оправдание.

anonymous
()
Ответ на: комментарий от anonymous

Это че, теперь исключения нельзя выбрасывать? Интересно, и какой ныне идиоматический способ сообщения об ошибке в крестах? А потом он говорит, что никто с крестами не знаком.

И ещё удивительно, насколько я помню, eao197 много раз нахваливал механизм исключений в цепепе, что в случае вложенности вызовов это способ сообщить об ошибке вниз по стеку... :-) Но тут потребовалось обосновать рекомендацию tailgunner по использованию библиотеки, в которой вместо значения результата парсинга вдруг возвращается std::string с ошибкой :-) Вот ведь аномалия :-)

anonymous
()
Ответ на: комментарий от eao197

Что плохого в сишечке, для начала?

anonymous
()
Ответ на: комментарий от eao197

Боюсь, вы, как обычно, смотрели в книгу, а видели лишь то, что хотели увидеть.

Это мне? Откуда цитата про страуструпа? Я задал четкий вопрос. Кто-то тут про факты балаболил, а вот оно опять, какое-то пустословие.

Вопрос был такой:

Если исключения депрекейтед, то:

какой ныне идиоматичный способ сообщения об ошибке в крестах?

anonymous
()
Ответ на: комментарий от anonymous

И пошла заливка про «ключи компилятора» и про поставленные в жёсткие рамки команды программистов на C++, которые вынуждены отказываться от большой части языка, который они же и применяют :-) Ну где логика, мне не понятно, например :-)

anonymous
()
Ответ на: комментарий от anonymous

Это че, теперь исключения нельзя выбрасывать?

Можно. Просто практика показала, что спецификатор throw оказался плохой идеей. Подробнее здесь: http://www.gotw.ca/publications/mill22.htm

Теперь, чтобы показать, что функция/метод не бросает исключение, используется спецификатор noexcept. Если спецификатора нет, то функция/метод может бросить все, что угодно.

eao197 ★★★★★
()
Ответ на: комментарий от eao197

Это не ответ на мой вопрос.

Еще раз, может с третьего раза дойдет:

какой ныне идиоматичный способ сообщения об ошибке в крестах?

anonymous
()
Ответ на: комментарий от anonymous

Речь про спецификатор, тот что в сигнатуре, а не оператор.

mix_mix ★★★★★
()
Ответ на: комментарий от eao197

Если спецификатора нет, то функция/метод может бросить все, что угодно.

Более того, как выясняется, она и вернуть может всё, что угодно :-) И для этого достаточно лишь одного типа данных - std::string :-) Лол :-)

anonymous
()
Ответ на: комментарий от anonymous

какой ныне идиоматичный способ сообщения об ошибке в крестах?

Нет такого. В проектах, где использование исключений разрешено, используют исключения. В проектах, где исключения запрещены, применяются разные подходы (будь то errno/SetLastError/GetLastError, или же коды возврата).

eao197 ★★★★★
()
Ответ на: комментарий от anonymous

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

Есть ли реализации JVM, в которых исключения запрещены в принципе?

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

eao197 ★★★★★
()
Ответ на: комментарий от eao197

Нет такого.

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

anonymous
()
Ответ на: комментарий от eao197

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

Откуда можно сделать вывод, что у цепепе проблемы :-)

anonymous
()
Ответ на: комментарий от anonymous

Класс с тремя полями/простенький шаблон в либе из наверное более тысячи строк — излишен?

В header-only либе парсинга JSON. Да, излишен.

Какое-то дешевое оправдание.

А ты попробуй привести какой-нибудь юзкейс для «класса с тремя полями».

Это мне?

Анонимусов различают только модераторы.

tailgunner ★★★★★
()
Ответ на: комментарий от anonymous

Так и надо было говорить сразу.

Позволю себе напомнить столь внимательному читателю, что речь шла о спецификаторе throw. А вовсе не об отмене исключений, как вам могло показаться.

Херово это крайне.

Ну уж как есть.

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

С-шные либы тоже бывают разные. В некоторых возвращается 0 как индикатор успеха, а все остальные значения — это коды ошибок. В некоторых возвращается -1 как признак неудачи, а код ошибки нужно смотреть в errno.

Так что без чтения документации и в C не обойтись.

И потом кто-то тут говорит про дешевую разработку на плюсах, когда разные либы даже сообщения об ошибках по-разному возвращают.

И вновь позволю себе указать столь внимательному читателю, что речь шла про более дешевую разработку на C++ по сравнению с C.

eao197 ★★★★★
()
Ответ на: комментарий от eao197

Нет такого. В проектах, где использование исключений разрешено, используют исключения. В проектах, где исключения запрещены, применяются разные подходы (будь то errno/SetLastError/GetLastError, или же коды возврата).

Ложь и подмена понятий :-) Тебя же спросили про идиоматичный способ, а не про существование проектов, в которых тужатся изо всех сил, чтобы избегать идиоматичных способов по каким-либо причинам :-) А еще в CppCoreGuidelines сказано следующее: «If you can't use exceptions (e.g. because your code is full of old-style raw-pointer use or because there are hard-real-time constraints), consider using a style that returns a pair of values» :-) Так что не надо сочинять :-)

anonymous
()
Ответ на: комментарий от eao197

Есть ли реализации JVM

Вряд ли, даже в эмбеддед жабах есть, вроде.

огромное количество народу начнет вопить

Это понятно. Только вот язык нужно пилить под задачу, и тут кресты в жопе.

Сишка прекрасный язык для эмбеддеда — она быстра, проста, но самое главное — предсказуема, за что ее так любят разработчики ядер, драйверов, а линус до сих пор ругает кресты именно за то. И она, что характерно, идиоматична. А кресты в эмбеддеде — это сишка с полиморфизмом и шаблонами, что ок, ибо m4 мне тоже не особо нравится, но они пытаются запилить в нее фичи, которые превращают ее в жабку, и это полный провал. Эти фичи нельзя использовать, они разворачиваются при компиляции в хрен знает что, тормозят, как те же исключения при выбросе, раздувают стандарт. А в итоге они это говно еще и объявляют устаревшим. Не язык, а помойка с целым зоопарком подходов к разработке. Их дело, конечно, каждый делает, как считает нужным, но как по мне левому человеку, который не дрочил кресты 10 лет к ряду, после скалы/жабки/питона/сишки будет архитрудно начать что-то писать на крестах. Даже с умными указателями.

anonymous
()
Ответ на: комментарий от anonymous

И ещё удивительно, насколько я помню, eao197 много раз нахваливал механизм исключений в цепепе, что в случае вложенности вызовов это способ сообщить об ошибке вниз по стеку... :-) Но тут потребовалось обосновать рекомендацию tailgunner по использованию библиотеки, в которой вместо значения результата парсинга вдруг возвращается std::string с ошибкой :-) Вот ведь аномалия :-)

Если это и аномалия, то только вашего восприятия действительности. Я всегда говорил, что исключения лучше, чем коды возврата. Но есть условия, когда исключения применять нельзя. И тогда уже ничего другого не остается.

eao197 ★★★★★
()
Ответ на: комментарий от anonymous

Сишка прекрасный язык для эмбеддеда

Эмбеддед - он очень разный бывает. И мигание диодами, и управляющие программы F-35 - эмбеддед.

ее так любят разработчики ядер, драйверов

Некоторые любят, да. Некоторые считают устаревшим ублюдочным говном.

tailgunner ★★★★★
()
Последнее исправление: tailgunner (всего исправлений: 1)
Ответ на: комментарий от eao197

Рекомендую почитать о разработке софта для управления двигателями на C++.

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

anonymous
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.