- 1
enum {size = 10, timeout = 50};
Нашли или выдавили из себя код, который нельзя назвать нормальным, на который без улыбки не взглянешь? Не торопитесь его удалять или рефакторить, — запостите его на говнокод.ру, посмеёмся вместе!
+142
enum {size = 10, timeout = 50};
В том смысле, что похоже, что timeout - это кол-во секунд соотвествующие timout-у в какой-то операции, а size - это размер какого-нибудь буфера.
поэтому константы в enum самые православные...
в новом стандарте обещали типизированный enum...
эти константы 100% компайл тайм...
к стати они допускают компайл тайм вычисления (если это возможно), допустим так
ну и те кто поопытней, знают что такой код:
> не говнокод 100%. у нас в кодгайдлайне такой метод рекомендован...
Говногайдлайны уж постить нельзя?
оптимизация такого дефайна
#define kAlignedSize(kSize) (kSize + 15) & (~0xF)
ляжет на плечи компилятора, и если оптимизации отключены или компилятор не понял идей аффтара, то вычисление переедет в рантайм...
в енаме компилятор гарантирует компайл тайм иначе будет ошибка...
В любом случае, это что касается "составных" дефайнов. В приведённом же примере имеем тупо числа, они 100% в любом самом засраном компиляторе будут компайл-тайм, т.е. конкретно приведённый пример есть говнокод, за остальное я не говорю.
s = ZHOPA;
после работы препроцессора выглядеть в коде будет так (если CONST1 == 1):
s = (1 + 1);
Теоретически гарантий может и нету, но практически они есть в любом адекватном компиляторе. Или ты считаешь, что компилятор будет тупо делать push 1; push 1; add?!
> поведение в дебаге и релизе будет совсем разным...
С чего бы? Объект константен вне зависимости от того, инициализируется он в рантайме или в компайлтайме. Ты не тяни сюда свой с++, мы не может сделать константный объект, который бы в своём конструкторе мог делать сайд-эффект на окружение. Да и в сиплюсе юзание сайд-эффектов при конструкции константного объекта было бы говнокодом. Поведение будет одно и то же. Или ты путаешь поведение с реализацией поведения?
Ага, call add. Сложение путём вызова подпрограммы.
если не понимаешь профита от компайл тайм вычислений так и скажи, не надо пытаться убеждать окружающих, что кактус вкусный и в сыром виде...
А по делу:
Компилитайм вычисления редко нужны. А там где нужны - экономия на спичках. И вообще, всё что можно посчитать во время компилитайма - можно посчитать и в другое время один раз. Например при старте приложения или в момент ипользования(линивые вычисления).
enum
const int
define
P.S. я против удаления define из С++, так как есть места где без него плохо, допустим в ASSERT...
Не надо меня готовить! Есть растения, более лёгкие в приготовлении.
Мне таких хаков задаром не надо... Внимательней будь и всё.
Один хуй после стряпания кода будешь юзать профайлер (или вы в вашей говноконторе их не юзаете?) и найти такое проблемное место будет довольно несложно (если оно действительно проблемное, а не тупое "premature optimization" в ущерб чистоте кода).
код должен говорить программисту о его ошибках!
Не тот язык выбрал, значит. Си именно что славится своей нестрогостью. И попытки сделать его строгим всегда останутся хитровыебанными хаками.
И-таки почитай про premature optimizations, опытный ты наш.
и она неприменима в 90% случаев в которой ее пытаются применить, так как эту цитату чаще применяют как отмазку своей неопытности, как в примере с тобой...
"преждевременная оптимизация - залог здорового говнокода"
=)
неоптимизированный код тоже может быть говнокодом...
> свертывание констант в компайл тайме это не оптимизация
Да в полне оптимизация.
Логически (если рассматривать как blackbox) программа будет получать одно и то же значение - по этому верно будет сказать, что значение - константно.
А вот как это значение в ассемблере реализуется - это уже детали реализации. То что ты предлагаешь - это хитровыебанные хаки, чтобы заставить компилятор генерировать нужный тебе ассемблер-код. Это, конечно, полезная идея, однако 99% кода особо остро не нуждается в компайл-тайм свёртке и в 99% случаев (исхожу из практики) комплиятор уже всё сам сворачивает в компайл-тайме. Исходя из этого можно сказать, что сий хак не стоит выеденного яйца (по крайней мере, чтобы пихать его всюду).
С юнит-тестами и валгриндами, я знаю, что мои программы правильные. Не всё же дебажить с помощью printf'ов...
int i = 0;
int zhopa = DOUBLE_ZHOPA(i++);
дефайны - в жопу!
literate programming?
что-то я не видел, чтоб его крестофилы использовали
я про то, если есть возможность написать код который не будет доставлять в будущем, то лучше это сделать...
define практически всегда невыдерживает рефакторинга, об ограничениях const я написал. я понимаю что это все в С++, но никто не мешает использовать это в С...
http://www.parashift.com/c++-faq-lite/misc-technical-issues.html
http://www.parashift.com/c++-faq-lite/inline-functions.html
И применение инкрементов в правой части тоже:
http://govnokod.ru/3535
http://lurkmore.ru/++i_+_++i
Макросы-константы вполне безобидны.
asm:
Gcc o3:
Уже сразу херачит 32... То же самое, если подставить, допустим, sizeof(int) - сразу оперирует с числом 16.
Но енумы все-таки лучше, они типизированы, разные вкусные штучки на уровне компилирования, например, если в свиче не все значения.
И их видно в дебугере!
Сделали б еще определение количества элементов, цены б ему не было, а то извращаться приходится.
но в таком случае - никогда.
ну и уж тем более нельзя загонять под один енум.
Иногда const int удобнее, не спорю.
Енум - легкое извращение.
А упор был на то, что в один енум запхнуть - это просто идиотизм.
Проще тогда вообще все константы модуля в один енум закинуть.
Идея-то в чем? изменить одно значение по необходимости в одном месте с минимальным усилием.
К тому же, если уж так смотреть на удобство дальнейшего использования, то дефайн позволяет потом сделать что-то вроде
#define timeout (getTimeout())
если ему нужна константа он создает константу, если ему нужна подстановка он использует дефайн...
к счастью, этот сайт всегда рад тем кто не понимает этого простого правила...
Почему к сожалению? О_о
большая часть темы, это:
- компилятор сделает все за меня
- зачем напрягать свой моск
- я уверен в том что этот говнокод рабочий
- ...
- premature optimisation
И при этом эти люди считают себя довольно крутыми программистами...
для с++, но не для с.
? 1 : 0;
[/quote]
Смотрите, смотрите, Пушков бульшитит!
>результат сравнения имеет тип bool, тернарный оператор для енамов считается в компайл тайме, если все его аргументы - константа...
Капитан Очевидность?
>единственная проблема в том куске кода это ;...
сам кусок кода :D
(int)(a>b)
Вообще, уже пора С/С++ разделы объединить.
Но тогда куча троллей останется без дела.
Для явного преобразования я вижу такие применения:
(актуально в Си, где еще не добавили bool)
onoff - массив типа, ведущего себя как bool ( т.е. 0 - ложь, всё остальное - истина )
mask - по сути битовая маска, которую потом в явном виде скармливаешь какой-нибудь многоканальной железке ввода/вывода.
Или например так:
P.S. А вот в С++ bool'ы по стандарту преобразуются в 0/1, и такие пляски уже ни к чему.
4.7.4 If the source type is bool, the value false is converted to zero and the value true is converted to one.
И я не говорю, что такой код неправилен в плане того, что создает какие-то ошибки. Он неправилен со стилистической точки зрения. Если уж надо использовать перечисление - то прямая дорога к двум различным енумам с одним определением.
код на самом деле выглядит еще немного ужасней, примерно так:
Что кагбе намекает на то, что PREFIX_SIZE - он той же единицы измерения, что и PREFIX_TIMEOUT.
основные претензии говнокодеров в том, что это енум, а не дефайн
Нет. Я тоже считаю, что нужно разносить логически не связанные константы по разным энумам.
Или ты меня считаешь не говнокодером? Обижаешь... Я настоящий говнокодер и иду по непревзойдённому говнокодному пути.
timeout - промежуток времени, часами мерить надо
size - размер, в килограммах/байтах/сантиметрах и т.д.
по названию по-моему, явно видно.
вот пример на C
enum {
size = 10,
timeout = 20
};
char buf[size];
...
read_data_with_timeout(&buf, size, timeout);
константы логически связаны
Вот это я ещё понимаю:
У дефайна нет scope, да и вообще это препроцессор и к языку никак не относится
А он, scope, зачем-то нужен?
> да и вообще это препроцессор и к языку никак не относится
Welcome to C.
> и при этом ты следишь за всеми файлами в проекте, не дай бог где-нибудь случайно появится еще один SIZE, не связанный с этим SIZE?
Это я для примера так написал. Сам-то я использую систему префиксов:
1) два символа, идентифицирующие проект
2) имя логического неймспейса
3) непосредственно значение
Напр.: CF_BUFFER_DEFSIZE
Легко, просто, вкусно.
Во-первых лично у меня имена так систематизированы, что пересечение крайне маловероятно. Во-вторых даже если будет пересечение, то компилятор ругнётся о переобъявлении.
Это как январь|февраль, НЕХ какая-то.
Но, может, это образование сказывается, кольца там, поля всякие. Воротит от непонятных, левых операций:)
Поэтому у меня все битовые флаги — это не енумы.
Но, наверное, это тараканы, никакой почвы под лапами не имеющие.
размер и таймаут - это величины разного порядка, а следовательно, в одном енуме они выглядят говёно.
Вполне нормальный код.
Всё-таки перечисление — это набор однотипных сущностей, а здесь время и количество. Но данный код только выглядит ужасно, а работать он должен. Хотя написать #define было бы нагляднее, чем плодить новые сущности.
Да. Пожалуй никто не погибнет. Лишь при прилунении лунохода, последний разлетится на мелкие кусочки из-за того, что тип энумв и другой переменной случайно совпали и ошибки компиляции не последовало.
Знаешь, сколько людей за эти деньги можно было вылечить от рака и спасти им жизнь?
Но раздел-то "си". Запостил бы автор сие в С++ - нареканий бы не было. Какими бы хаками с++-дитя не тешилось...
"где здесь С++?"
и не стыдно? =)
http://govnokod.ru/3508
непотребное ООП компилятор не поддерживает.
Так зондеркоманда в Интернете всё-таки существует! А что нам за плюсы и минусы будет? Как в поисковике: мы вопрос, а Вы ссылку?