реклама на сайте
подробности

 
 
3 страниц V  < 1 2 3 >  
Reply to this topicStart new topic
> CPP enum с минусовыми значениями, насколько это правильно
novikovfb
сообщение May 26 2017, 09:46
Сообщение #16


Знающий
****

Группа: Участник
Сообщений: 518
Регистрация: 29-09-11
Пользователь №: 67 450



Цитата(AnatolyT @ May 26 2017, 13:11) *
Непонятно какие преимущества дает использование enum как типа возвращаемого значения функции.

1. компилятор проверит тип, если есть 2 различных функции, возвращающих коды завершения, имеющих разные наборы значений (и разные enum) - при перепутывании будет предупреждение.
2. символические константы содержат намек на смысловое значение кода, меньше гадать, что означает возврат кода 4.
Go to the top of the page
 
+Quote Post
Сергей Борщ
сообщение May 26 2017, 09:54
Сообщение #17


Гуру
******

Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095



QUOTE (novikovfb @ May 26 2017, 12:46) *
при перепутывании будет предупреждение.
В плюсах. В обычных Сях enum неявно приводится к int и обратно, поэтому предупреждения, насколько помню, не будет.

Добавлено: перечитал название темы...


--------------------
На любой вопрос даю любой ответ
"Write code that is guaranteed to work, not code that doesn’t seem to break" (C++ FAQ)
Go to the top of the page
 
+Quote Post
k155la3
сообщение May 26 2017, 10:01
Сообщение #18


Профессионал
*****

Группа: Свой
Сообщений: 1 123
Регистрация: 8-03-09
Из: Днепр
Пользователь №: 45 848



Цитата(AnatolyT @ May 26 2017, 12:11) *
Непонятно какие преимущества дает использование enum как типа возвращаемого значения функции.

Кроме очевидных преимуществ-удобств разгружающих моск.
Если Вы определили возвр. значение с типом enum, то при работе на отладке
Вы в Watch-окне будете видеть не абстрактные 12345 (и декодировать их вручную),
а символическое имя - в удобо-читаемом-понимаемом виде.

Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 26 2017, 10:10
Сообщение #19


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



По-моему идеально использовать enum по возможности так, чтобы было вообще всё равно какое там у него значение.
Оно так автоматически и получается, если везде работать с enum как с типом, а не пользоваться тем, что он может быть неявно преобразован в int.

Если все ошибки в вашей системе перечислены в enum и вам не нужно обеспечивать совместимость со сторонним кодом, где у ошибок есть конкретные int значения, то определите для ошибок тип
Цитата
typedef enum{
ERR_OK,
ERR_SOMETHING,
ERR_SOMETHING2
} Error_t;


Пусть все функции будут возвращать Error_t, а обработчики ошибок везде будут реагировать на ошибки путем обращения к ним по именам ERR_OK, ERR_SOMETHING, ERR_SOMETHING2 то всё будет отлично.
Код
switch( error)
{
case ERR_OK: делаем что-то
break;
case ERR_SOMETHING:
break;
case ERR_SOMETHING2:
break;
}

Это будет работать вне зависимости от значений энумов.

Eсли функция возвращает int а мы делаем return ERR_SOMETHING; который вообще-то Error_t - это дурной тон.
Потом чтобы обработать эту ошибку нам надо этот инт опять кастить в enum и начинается каша. Потом кто-то подставит вместо ERR_SOMETHING магическое число какое-нибудь и оно работает. Через год в энум Error_t доавбяют сверху пару новых кодов ошибок, значения все съезжают и то самое магическое число начинает указывать на другую ошибку. Начинается очень большое веселье.

Систему типов компилятора надо использовать, а не бороться с ней!


--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post
AnatolyT
сообщение May 26 2017, 10:25
Сообщение #20


Частый гость
**

Группа: Участник
Сообщений: 176
Регистрация: 29-03-10
Пользователь №: 56 269



Может быть чтобы не было соблазна добавить в начало enum новый код ошибки лучше однозначно закрепить код ошибки в define, потом все равно разбирать его в switch case. Другое дело если используем enum, тогда можно одновременно вести массив строк с сообщениями об ошибках, в порядке соответствующем enum, хотя тоже самое можно делать и с кодами определенными в define.

Сообщение отредактировал AnatolyT - May 26 2017, 20:04
Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 26 2017, 10:58
Сообщение #21


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



Цитата
Может быть чтобы не было соблазна добавить в начало enum новый код ошибки лучше однозначно закрепить код ошибки в define,
Может, если в коде не будет ненужных приведений типов и магических цифр - можно доавбялть в энумы что угодно и куда угодно?

Enum - это не define. Дискутировать в плоскости enum vs define не корректно.
Так можно и до define vs template дойти.... это всё глупости.


--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post
AlexRayne
сообщение May 26 2017, 13:33
Сообщение #22


Местный
***

Группа: Участник
Сообщений: 319
Регистрация: 27-09-07
Пользователь №: 30 877



Цитата(sigmaN @ May 26 2017, 13:10) *
Код
typedef enum{
ERR_OK,
ERR_SOMETHING,
ERR_SOMETHING2
} Error_t;

sigmaN: а почему Вы большими буквами значения енума определяете?

Сообщение отредактировал AlexRayne - May 26 2017, 13:33
Go to the top of the page
 
+Quote Post
k155la3
сообщение May 26 2017, 14:38
Сообщение #23


Профессионал
*****

Группа: Свой
Сообщений: 1 123
Регистрация: 8-03-09
Из: Днепр
Пользователь №: 45 848



Цитата(AlexRayne @ May 26 2017, 16:33) *
sigmaN: а почему Вы большими буквами значения енума определяете?

Ну например, #def в проекте мало. А кодов на базе enum - очень много, и надо чтоб они хорошо выделялись из текста.
Если нет какой-либо корп. политики-правил, то это дело целесообразности-удобства для аффтора sm.gif
Я использую префикс eSET_MODE_RUN - с макросами уже не путаются.
IMHO.

Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 26 2017, 15:45
Сообщение #24


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



Цитата
а почему Вы большими буквами значения енума определяете?
да это всё дело вкуса на самом деле... Это как раз не принципиально.


--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post
dxp
сообщение May 27 2017, 05:21
Сообщение #25


Adept
******

Группа: Свой
Сообщений: 3 469
Регистрация: 6-12-04
Из: Novosibirsk
Пользователь №: 1 343



QUOTE (sigmaN @ May 26 2017, 22:45) *
да это всё дело вкуса на самом деле... Это как раз не принципиально.

Скорее не вкуса, а стиля. Заглавными символами принято описывать неизменяемые сущности типа констант, литералов.
CODE
#define SLON 1
const uint32_t MAMONT = 10;
enum TSlon
{
    KOT = 20,
    BEGEMOT
};

...

TSlon Slon = KOT;

uint32_t x = Slon == BEGEMOT ?  MAMONT : SLON;


Сразу видно, где переменные, а где константы/литералы. Устоявшийся стиль. Стараюсь придерживаться его.


--------------------
«Отыщи всему начало, и ты многое поймёшь» К. Прутков
Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 28 2017, 09:13
Сообщение #26


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



Кстати вы заметили, как в С++11 поправили enum? Я имею ввиду enum class.
Убрали возможность неявного приведения к int, ограничили областть видимости перечислений?

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


--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post
jcxz
сообщение May 28 2017, 10:26
Сообщение #27


Гуру
******

Группа: Свой
Сообщений: 5 228
Регистрация: 3-07-08
Из: Омск
Пользователь №: 38 713



Цитата(k155la3 @ May 26 2017, 12:01) *
Кроме очевидных преимуществ-удобств разгружающих моск.
Если Вы определили возвр. значение с типом enum, то при работе на отладке

Enum в аргументах/результатах функций это конечно правильно и удобно в отладке, но к сожалению например IAR при работе с enum-аргументами функции вставляет в каждой операции команды расширения байт->слово.
Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 28 2017, 11:17
Сообщение #28


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



Цитата
The enum type
The compiler will use the smallest type required to hold enum constants, preferring
signed rather than unsigned.
When IAR Systems language extensions are enabled, and in C++, the enum constants
and types can also be of the type long, unsigned long, long long, or unsigned
long long.
To make the compiler use a larger type than it would automatically use, define an enum
constant with a large enough value. For example:
/* Disables usage of the char type for enum */
enum Cards{Spade1, Spade2,
DontUseChar=257};

http://supp.iar.com/FilesPublic/UPDINFO/00...opmentGuide.pdf page 227



--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post
dxp
сообщение May 28 2017, 13:02
Сообщение #29


Adept
******

Группа: Свой
Сообщений: 3 469
Регистрация: 6-12-04
Из: Novosibirsk
Пользователь №: 1 343



QUOTE (sigmaN @ May 28 2017, 16:13) *
Кстати вы заметили, как в С++11 поправили enum? Я имею ввиду enum class.
Убрали возможность неявного приведения к int, ограничили областть видимости перечислений?

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

Да, улучшения налицо. Только enum class - это, я понял, как раз создание пространства имён для элементов перечисления, а тип там указывается, например, как enum EnumName : uint32_t (тип можно использовать любой целый, который подходит для хранения представления).

Жаль, что некоторые популярные компиляторы - например, IAR, - не поддерживают C++11. Или я отстал о жизни?


--------------------
«Отыщи всему начало, и ты многое поймёшь» К. Прутков
Go to the top of the page
 
+Quote Post
sigmaN
сообщение May 28 2017, 13:50
Сообщение #30


I WANT TO BELIEVE
******

Группа: Свой
Сообщений: 2 617
Регистрация: 9-03-08
Пользователь №: 35 751



Цитата
Только enum class - это, я понял, как раз создание пространства имён для элементов перечисления
Ну и это и плюс отсутствие неявного преобразования в int.

Код
enum class Color {RED, GREEN, BLUE};  
int i = Color::RED; //compiler error!
int i = static_cast<int>(Color::RED); //Ok


Т.е. именно более сильная типизация во всех её проявлениях.


--------------------
The truth is out there...
Go to the top of the page
 
+Quote Post

3 страниц V  < 1 2 3 >
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 8th July 2025 - 00:50
Рейтинг@Mail.ru


Страница сгенерированна за 0.03457 секунд с 7
ELECTRONIX ©2004-2016