Как стать автором
Обновить

Комментарии 44

я не утверждаю, что с++ умирает, но тем не менее на яве это будет так:

int value = 100500;
int byte = value >>> 24; //хотя не знаю сколько тут будет тактов
Дожили. То, что есть возможность получить старший байт за 1 такт — это главное преимущество языка…

Хотя… Если буду вдруг писать программу, которая только и делает, что получает этот байт, то, следуя Вашему совету обязательно возьму C++
НЛО прилетело и опубликовало эту надпись здесь
НЛО прилетело и опубликовало эту надпись здесь
Именно это я пытался продемонстрировать. Я не пишу на одном С/C++. Я пишу и на С# и на Java и Python пробовал, и для себя давно определил где когда и какой язык применять, тут я попытался показать на простом примере, что есть области где большинство из современных языков просто не применимы, или точнее будут неэффективны.
OCaml'овский сборщик мусора, по непроверенным слухам, оказывается для некоторых задач эффективнее ручной работы с памятью.

А если учесть, что большинство программистов С++ обмазываются высокоуровневыми обертками для указателей… пичаль-пичаль.
Это из вчерашней статьи? Хех. И ведь пойдет же «слух» в массы. При том, что «эксперимент» поставен КРАЙНЕ некорректно.
С одной стороны декларативный ocaml, который все эти cons-списки, кложуры и карринг воспринимает чисто семантически и в конце концов может делать с кодом что угодно.
С другой стороны, императивный C++, на котором императивно же записаны все те же cons-списки и кложуры. Ну не может C++ «соптимизировать» выделение памяти и апдейт поля cons-пары, если он не можут доказать, что эти данные потом не используются. Не имеет права, а раз передаются параметром, значит используются. Ну дык никто и не пишет на C++ явно выделяя cons-пары и кложуры и копируя их туда сюда по значению. Для «функционального стиля» есть <functional>, <algorithm> и прочие.

Если уж пошли такие подтасовки, я могу заявить, что на ocaml ВООБЩЕ НЕЛЬЗЯ переписать ни одну C++ программу (технический проигрыш — игрок не явился на соревнование) так как main имеет два аргумента, а каррирующие языки в принципе не поддерживают функций более одного аргумента.

И да, в той же статье сказана глупость про невозможность достижения O(const+) времени выделения динамической памяти, что в общем свидетельствует о познаниях автора в C++ не хуже, чем его «C++ порт ocaml программы».
a' -> b' -> c' — вполне можно считать функцией двух аргументов.

Что же касается «функционального стиля» на С++ — последняя реализация карирования функции, которую я видел, была настолько отвратительна, что стало ясно, что ФП С++ не поддерживает в принципе.

С++ — императивный язык с поддержкой ООП, не более того. Он оброс тонной ненужной ерунды, которая сделала из него совершенно непонятного монстра.

Императивный подход к программированию, в принципе, как у вас отмечено, тем и плох — что программиста заставляют слишком много думать. Ему надо писать бизнес-логику — а он сидит в указателях и алгоритмах сортировки. Декларативность спасает от таких проблем.
> a' -> b' -> c' — вполне можно считать функцией двух аргументов.
Нет нельзя. Это функция одного аргумента, возвращающая функцию одного аргумента, о чем явственно свидетельствует запись. На C++ n-queens тоже «можно» написать без консов и кложур (вернее именно так напишет любой, кто имеет хоть немного C++ опыта и желает получить достоверные результаты, а не очередное «доказательство преимущества»).

> Императивный подход к программированию, в принципе, как у вас отмечено, тем и плох — что программиста заставляют слишком много думать.
А вот здесь соглашусь всеми конечностями. Даже не потому, что «много думать» сложно, а потому, что если программист сильно много думает — у компилятора остается слишком мало «пространства для маневра».

Другое дело, что «sufficiently clever compiler» пока не изобрели и на императивном C++ получаются более производительные программы. Period. Не стоит пытаться «забороть» плюсы на его же поле — нужно, как правильно указано в том посте, упирать на скорость/удобство разработки/поддержки. И уж тем более не стоит сравнивать эффективность general purpose аллокатора на C++ со скоростью окамловского выделения на стеке (а в n-queens простейший flow control analysis покажет, что переменные нужно выделять именно в стеке и куча совершенно ни к чему).
На С++ можно написать более производительную программу, но трудозатраты, трудозатраты.

Для конкретных же задач гораздо лучше подходят другие языки программирования.

С++ — это ступень последней надежды, когда больше не на чем писать — программа пишется на С++, с диким количеством кода, огромным числом багов и глючной реализацией половины Common Lisp.
Трудозатраты часто переоцениваются. Причем переоцениваются зачастую теми, кто на C++ не пишет: на том же google codejam (где учитывается как раз таки время, затраченное на решение) стабильно 7-8 первых мест из десяти — на C++. В ICFP (где, в конечном итоге, тоже все упирается во время) тоже с завидным постоянством побеждают C++ команды (и это на FP контесте!!!).

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

Что же до гринспуна и его правила — уж очень оно мне напоминает «народную мудрость», которую можно услышать только от толстых женщин: «В результате опроса половина мужиков призналась, что им нравятся толстые, другая половина просто не призналась в этом».
На codejam маленькие и интересные задачки, а в жизни чаще всего огромные и рутинные.
Вы правы, многие люди действительно пишут программы на С++ с диким количеством кода и огромным числом багов. Только вот непонятно, почему ругают за это сам язык, а не людей, неправильно его использующих?.. Вы не знаете?..
а каррирующие языки в принципе не поддерживают функций более одного аргумента.
Передача много аргументов за раз = передача кортежа, что поддерживается без проблем
Окамла под рукой нет, но будем считать эфшарп окамлдотнетом:
> let add a b = a + b;;
val add : int -> int -> int

> add 1;;
val it : (int -> int) = <fun:it@8-2>

Никаких туплов — функция одного аргумента, возвращающая фунарг. Это и есть карринг (в отличие от частичного применения, которое часто путают с каррингом).
Я знаю что такое карринг.

я имел ввиду это:
let add (a, b) = a + b;;
add 1;; (* ошибка: передали int, ожидали int * int *)
Это все равно один аргумент. C++ аналогом будет std::tr1::tuple
Функций нескольких аргументов нет. На всякий случай, я не вижу в этом вообще никакой проблемы — я просто пытаюсь передергивать так же как автор этой статьи
Как человек, который программирует на c++ 95% своего кода, хочу спросить: разве Ваше решение не нарушает strict aliasing и не ведёт себя по-разному на big-endian и little-endian машинах? И побитовый сдвиг в других языках никто не отменял, другое дело, что в интерпретируемых языках это будет явно не один такт, ровно как и любое арифм. действие.
Насколько я знаю C# и Java компилируются в машинный код во время выполнения. У Java даже есть аппаратная поддержка — технология Jazelle, реализуемая в некоторых ARM-процессорах.
Доколе в эпоху гигабайтов и гигагерцов мейнстримной задачей будет получения старшего байта четырехбайтного целого?

rsdn.ru/Forum/Info/FAQ.philosophy.culture.aspx

Если мне понадобится решить эту задачу — я напишу маленькую DLL на чистом C. Или даже маленькую программу. И запущу ее из огромного монстра, написанного на каком-нибудь C#, который решает задачи в миллион раз сложнее, чем выделение старшего байта.
Значит таки напишете:) А выше показанный пример ни как не является аргументом в выборе языка для ворочения гигабайтами, а всего лишь иллюстрацией того, что есть задачи где многие языки просто неэффективны.
Естественно. Но именно на C, а не монструозном подобии языка программирования высокого уровня под названием С++.

С — язык программирования низкого уровня. С++ — убогое говно, которму самое время умереть.

Хотя, за последние 4 года профессиональной деятельности, вопрос быстродействия приложения у меня встал однажды — в единственном моем написанном на (сюрприз!) С++ большом проекте.
Гавнопроект — это признак кривых рук, а не кривого языка.
Почему-то на других языках даже с моими кривыми руками никаких проблем с производительностью не возникало.
Я, вообще-то, не имел ввиду конкретно ваши руки.
НЛО прилетело и опубликовало эту надпись здесь
Premature optimization is root of all evil © Да, есть места, где именно это может стать бутылочным горлышком. Но, к удивлению, это бывает не во всех задачах и приложениях.
D:
int number;
byte mByte=*((cast(byte*) &number) + 3);

Problems, officer?
А вообще задолбали уже оправдываться. Обидели C++ и теперь всю неделю будем читать толстые вбросы и наезды.
Выполняется может и за один такт, но читается это очень сложно (честно говоря не понял как так получается).
Давайте поставим вопрос по-другому. Что умеет С++ такого, чего не умеет С, и при этом умеет это лучше других языков?

Классы? За ключевое слово friend надо отрывать руки дизайнерам языка, в том же C# без него вполне обошлись. ООП как ООП, никаких тебе code contracts, никакой информации о классах кроме RTTI, и тот работающий через задницу.

Шаблоны? Замечательная реализация, которая на каждое определение нового класса на основе шаблонного генерит тучу кода — до такого даже Java не опускалась, хотя у нее встроенной поддержки generics никогда не было. Да, лучшие умы в рамках boost умудряются на шаблонах творить чудеса (хотя эти чудеса не идут ни в какое сравнение с возможностями метапрограммирования на CL или том же Nemerle), которые радуют нас вырвиглазным write-only кодом и крайне запутанной логикой поведения. А быстродействие подобных решений чаще всего удручает — почитайте тот же RSDN, сколько людей отказались от буста в пользу своих велосипедов, более узкоспециализированных?

Макросы? За нетипизированные макросы С надо убивать убивать убивать. Они — источник огромного количества ошибок, которые затруднительно обнаружить.

Что дальше? Никакой поддержки автоматического распараллеливания алгоритмов (#pragma OMP не предлагать, это писец, а не решение), никакого тебе нормального foreach, отсутствие контрактов (ASSERT можно в жопу себе засунуть), слабые зачатки метапрограммирования, невозможность писать в CPS, никакой интроспекции, никакой динамической кодогенерации, ручная работа с памятью.

Никто не пробовал на С++ написать DSL?

По факту, С++ поддерживает две парадигмы — структурное программирование и ООП. Никакого АОП, никакого ФП, никакого программирования на контрактах. Кто сказал, что он мультипарадигменный?
не тучу, а только то что используется… в своем языке вы решаете это копипастой…
нет, мой язык решает это за меня — duck typing же
Насчет макросов это Вы зря, без них иногда просто не обойтись.
Давайте поставим вопрос по-другому. Что не умеет С++ такого, что умеет С или какой либо другой язык с более качественными компиляторами?
Ваш код — UB. Вопросы?
По-честному инструкции две — нужна еще одна инструкция пересылки из регистра в результат
То же самое так же работает и в С#
unsafe
{
int number = ( 1<<27)+5;
byte mByte = *(((byte*)&number) + 3);
}

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

Комбинирование — вот ключ к успеху.
Если вы пишите, к примеру, код для работы со сложной бизнес-логикой и вам не важны сэкономленные 1с, то для чего вам писать все на C++ — возмите C# с его .NET
Если вам нужно выполнить кусок кода быстро — возьмите ассемблерную вставку, «гарантированно компилируется в однотактную инструкцию практически на любом процессоре».

На самом деле, часто бывает, что выбор языка диктует не скорость обработки, а маркетинг и уже существующие наработки, что иногда удручает.
ТС, а оно Вам надо? Зачем кому-то что-то доказывать, что Вы для себя решили? Я во вчерашнем посте не стал отписываться даже.

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

Я ни в коем случае не хочу сказать, что C++ лучше, чем остальные языки, но уж точно не хуже и позволяет решать определенный класс задач лучше, чем остальные языки(в то же время, как некоторые задачи удобнее решать НЕ на c++). И как бы мы не хотели отправить его на свалку, этого не случится еще очень долго.

Чувствую себя унылым Кэпом…
>а что у Вас
ASM. x86-инструкция SHRD. ну и где твой бог теперь?
правильней делать сдвигом, так как ендианес разный на разных машинах никто не отменял.
Автору стоит посмотреть на Computer Language Benchmarks Game ( shootout.alioth.debian.org/u32q/benchmark.php ), где собраны различные алгоритмические задачки и принимаются их решения на различных языках. Решения затем тестируются на корректность и скорость, а результат наглядно можно видеть в табличках.
На мой взгляд, в сводной таблице отображается реальное положение дел (give or take). Вполне можно найти задачки, где Lisp или Fortran опережает решение на C++. Возможно автору будет интересно поучаствовать в написании более быстрых решений.
«И считаю, что рассматривать С++ в отрыве от возможностей С никак нельзя, хотя-бы потому, что все же он проектировался как наследник С.»
Это заблуждение. Очень вредное заблуждение. Современный С++ не имеет к С практически никакого отношения. Я подчёркиваю, как бы категорично это ни звучало: никакого отношения. С++ и С — это два разных языка программирования, с разной философией и разными сферами применения. Да, С++ произошёл от С, но это — лишь историческая данность прошлого века.
long frol;
char chol;
__asm
{
mov eax, frol
mov chol, al
}

Так-то, учите асм, хотя CPP мой любимый язык.
Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Изменить настройки темы

Истории