Название: Достоинства static_cast Отправлено: Igors от Сентябрь 18, 2012, 12:44 Добрый день
Навеяно этим Поэтому в C++ специально сделали безопасный статик_каст, а за C style cast надо по рукам бить. Сколько я уже наслышался проблем из-за него. Хочу услышать. Всем понятно что static_cast - это как бы "показатель грамотности", и я с этим полностью согласен. Однако можете ли Вы привести примеры (и побольше) где static_cast работает корректно, а вот С приведение - нет? Я лично затрудняюсьСпасибо Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 18, 2012, 13:06 Допустим, С каст игнорирует константность.
const char *const a = new char; int *b = static_cast <int*> (a); - ошибка int *c = (int*) (a); - все нормально Название: Re: Достоинства static_cast Отправлено: CuteBunny от Сентябрь 18, 2012, 16:44 Мой пример:
Код
Как мне видется нужность static_cast в том, что он проверяет на стадии компиляции является ли объект А объектом Б, т.е. банально проверяется отношение is-a, если А не есть Б, то такое преобразование ошибочно... Поправьте, если ошибаюсь, я еще всё еще чайник:) Название: Re: Достоинства static_cast Отправлено: xokc от Сентябрь 18, 2012, 21:40 Всем понятно что static_cast - это как бы "показатель грамотности", и я с этим полностью согласен. А вот я с этим совершенно не согласен. Если человек понимает отличие "cast" друг-от друга, то ему никогда этот самый static_cast и не понадобится. Использование"cast" как табу и показателя грамотности - есть абсолютное зло, в стиле "я не знаю ПОЧЕМУ теперь принято в инкременте цикла использовать ++i, а не i++, но (на всякий случай) пишу именно так, поскольку это - "показатель грамотности".Название: Re: Достоинства static_cast Отправлено: Akon от Сентябрь 18, 2012, 22:19 +CuteBunny
Основное достоинство в том, что static_cast не "опускается" до reinterpreta, в то время как С-стайл запросто. По инкременту - желательно всегда использовать в циклах одну форму, т.е. поступать единообразно. Префиксный предпочтительней, поскольку для некоторых типов (пользовательских) выше быстродействие, связанное с возвратом ссылки а не объекта. Название: Re: Достоинства static_cast Отправлено: LisandreL от Сентябрь 18, 2012, 23:42 Основное достоинство в том, что static_cast не "опускается" до reinterpreta, в то время как С-стайл запросто. reinterpret - это ещё не вся глубина падения. С-стайл каст делает ещё и const_cast.И если у reinterpret'а я запросто могу придумать разумные применения ( ну, например добавление данных при через QByteArray::append ( const char * str, int len ) ), то если вам понадобился const_cast, то почти наверняка у вас (или у используемой вами библиотеки) что-то не так с кодом. Ну а так по кастам: dynamic_cast и qobject_cast - могут использоваться для проверки типа объекта, если он точно неизвестен. Static, reinterept и const касты генерируют ошибку времени и в общем-то просто могут уберечь от ошибки в коде. Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 19, 2012, 07:10 +CuteBunny Основное достоинство в том, что static_cast не "опускается" до reinterpreta, в то время как С-стайл запросто. Цитировать Что делает приведение типов в стиле С: пытается использовать static_cast, если не получается, использует reinterpret_cast. Далее, если нужно, использует const_cast . Приведение типов в C++ (http://alenacpp.blogspot.com/2005/08/c.html)Цитировать если вам понадобился const_cast, то почти наверняка у вас (или у используемой вами библиотеки) что-то не так с кодом. Значит с STL что-то не так, т. к. у std::map нет константного operator[].Название: Re: Достоинства static_cast Отправлено: Akon от Сентябрь 19, 2012, 09:04 Цитировать reinterpret - это ещё не вся глубина падения. С-стайл каст делает ещё и const_cast. Да, защита от потери константности тоже большое дело.Цитировать то если вам понадобился const_cast, то почти наверняка у вас (или у используемой вами библиотеки) что-то не так с кодом Правильно.Цитировать Значит с STL что-то не так, т. к. у std::map нет константного operator[]. У него семантика такая. Для конст. мапа и поиска есть std::map::find().Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 19, 2012, 09:32 Значит с STL что-то не так, т. к. у std::map нет константного operator[]. В новом стандарте есть: const T & at( const Key& key ) const; (since C++11) Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 19, 2012, 09:54 В новом стандарте есть: 1. Не все компиляторы поддерживают C++11;const T & at( const Key& key ) const; (since C++11) 2. Не все компиляторы поддерживают стандартные исключения. Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 19, 2012, 10:01 1. Большинство уже поддерживает.
2. Всегда есть std::map::find, как уже сказали выше. Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 19, 2012, 10:06 У него семантика такая. Для конст. мапа и поиска есть std::map::find(). find() возвращает итератор, который в случае отсутствия элемента будет container.end();Проверить наличие элемента в мапе я могу простым count, а вот получить значение через operator[] не могу. На лицо явная проблема с удобством использования. Бывают такие структуры данных, которые используют частотные характеристики данных, и меняют свое состояние от каждого запроса на поиск, в этом случае что? Запилим mutable и константые методы? Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 19, 2012, 10:09 1. Большинство уже поддерживает. gcc-3X не поддерживает, да и сам стандарт не полностью поддерживается компиляторами. Это все привязка к компиляторам и реализациям STL, которую лучше избегать если нужна кроссплатформенность.Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 19, 2012, 10:21 1. Большинство уже поддерживает. gcc-3X не поддерживает, да и сам стандарт не полностью поддерживается компиляторами. Это все привязка к компиляторам и реализациям STL, которую лучше избегать если нужна кроссплатформенность.А Qt4 разве собирается с gcc-3Х? Если так завязываться за старое, никакого прогресса не будет. Название: Re: Достоинства static_cast Отправлено: LisandreL от Сентябрь 19, 2012, 11:11 А Qt4 разве собирается с gcc-3Х? 4.5 собиралось. http://www.prog.org.ru/topic_12303_0.htmlЗначит с STL что-то не так, т. к. у std::map нет константного operator[]. Ну если б с ней было всё так, её б не меняли с приходом нового стандарта.Проверить наличие элемента в мапе я могу простым count, а вот получить значение через operator[] не могу. Код
Бывают такие структуры данных, которые используют частотные характеристики данных, и меняют свое состояние от каждого запроса на поиск, в этом случае что? Ну, если они меняются, то константой они быть не могут (с точки зрения логики, а не возможностей языка).Запилим mutable и константые методы? Хотя ваш вариант сработает. Название: Re: Достоинства static_cast Отправлено: Igors от Сентябрь 19, 2012, 11:45 Попробуем подытожить чем лучше static_cast
- не позволяет (на этапе компиляции) привести типы которые не могут быть совместимы - соблюдает константность Хмм... пока больше ничего по существу не слышал :) От себя добавлю - исключает возможность перепутать с перекрытым оператором (напр char*) - хорошо заметен в коде (по-моему главное) Смущает однако почти полное отсутствие примеров, да и имеющиеся не очень убедительны Код Сравнивая это с топорным (QLineEdit *) w, - там мы падаем с 9-го этажа, а тут с 7-го. Да, наши шансы на выживание повышаются, но так ли уж значительно? :) По поводу "ах, потеряли константность - как низко мы пали!" и.т.п. Давайте я создам др тему? По константности есть что обсудить - и много, но мешать все в кучу нехорошо Название: Re: Достоинства static_cast Отправлено: lesav от Сентябрь 19, 2012, 12:16 Падая с этажа можно и парашют прихватить
Код
Название: Re: Достоинства static_cast Отправлено: lesav от Сентябрь 19, 2012, 12:29 Пардон, static_cast в таком случае бесполезен.
Условие срабатывает только с dynamic_cast Название: Re: Достоинства static_cast Отправлено: Bepec от Сентябрь 19, 2012, 12:56 Помоему все касты - есть лишь:
1) заметность в коде 2) ясность чего хотел пишущий эту строку программист 3) в последнюю очередь это проверки :) PS для меня удобнее будет увидеть статик каст и понять, что могут поступить неверные данные, чем смотреть на одинаковые (QLineEdit *) :) Название: Re: Достоинства static_cast Отправлено: Igors от Сентябрь 19, 2012, 13:18 Ну хорошо, а вот примерчик (видел у Вити которого что-то пока не видно - занят наверно)
Код Понятно "дело вкуса", но все же - уместно ли такое использование static_cast? Является ли оно "хорошим тоном" или так - понты? Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 19, 2012, 13:30 Скорее тогда уже не "дело вкуса", а придерживание единого стиля. Что значит не так уж мало.
Название: Re: Достоинства static_cast Отправлено: Akon от Сентябрь 19, 2012, 13:54 Код: QWidget * w; Код: d = static_cast <double> (f); Код: int i = 0x11223344; Название: Re: Достоинства static_cast Отправлено: Bepec от Сентябрь 19, 2012, 13:58 Тащить boost в Qt-шный проект это конечно же хорошо :)
И да, вы обламываетесь потому, что так написали :) Название: Re: Достоинства static_cast Отправлено: LisandreL от Сентябрь 19, 2012, 13:59 Сравнивая это с топорным (QLineEdit *) w, - там мы падаем с 9-го этажа, а тут с 7-го. Незначительно, но и стоит это нам только несколько дополнительных набранных символов. Проверки происходят на этапе компиляции, так что в производительности мы не потеряем (хотя и это не всегда критично).Условие срабатывает только с dynamic_cast С незанулённым указателем не сработает.Название: Re: Достоинства static_cast Отправлено: Igors от Сентябрь 19, 2012, 14:14 Скорее тогда уже не "дело вкуса", а придерживание единого стиля. Что значит не так уж мало. То есть это правильно, хорошо? Тогда прошу показать как написать напр такой кусочек (максимально упрощенный) в хорошем стиле приведенияКод
Название: Re: Достоинства static_cast Отправлено: CuteBunny от Сентябрь 19, 2012, 15:35 Ну хорошо, а вот примерчик (видел у Вити которого что-то пока не видно - занят наверно) Код Понятно "дело вкуса", но все же - уместно ли такое использование static_cast? Является ли оно "хорошим тоном" или так - понты? Мне кажется: Код бессмысленная запись, т.к. d = f - ничего страшного не будет и по стандарту написано, что float to double conversion is safe, float же меньше double и поэтому никаких потерей точностей не будет... Код
здесь да дело вкуса, можно static_cast<float>, можно (float) - в принципе оно быстрее по написанию... Название: Re: Достоинства static_cast Отправлено: CuteBunny от Сентябрь 19, 2012, 15:55 Скорее тогда уже не "дело вкуса", а придерживание единого стиля. Что значит не так уж мало. То есть это правильно, хорошо? Тогда прошу показать как написать напр такой кусочек (максимально упрощенный) в хорошем стиле приведенияКод
Думается мне это таким образом: Если напишу так: Код
значи я знаю, что у меня никогда не будет потерей точностей и говорю это компилятору, чтобы не сыпал варнинг... Хотя мне кажется тут на лицо, опасность, т.к. double'ы умножаются потом еще и складываются, когда-нибудь выстрел будет в ногу... поэтому если я не уверен, что (x * m.m00 + y * m.m10) и (x * m.m10 + y * m.m11) - поместится во float, я вообще не буду писать никаких приведениев ни в С++ стиле ни в Си, оставлю так, пусть компилятор говорит мне об потенциальной опасности в будущем... Название: Re: Достоинства static_cast Отправлено: V1KT0P от Сентябрь 19, 2012, 20:53 Ну хорошо, а вот примерчик (видел у Вити которого что-то пока не видно - занят наверно) Тут уже сказали основное. У меня привычка кастить примитивные типы появилась после того, как без каста код который вроде как должен нормально работать работал не так как надо(если очень интересно, то я могу попробовать порыться в старых исходниках и найти участок где отсутствие каста приводит к неправильному поведению). Также каст примитивных типов служит явным выделением участка кода к которому надо присмотреться, может там затаилась ошибка.Понятно "дело вкуса", но все же - уместно ли такое использование static_cast? Является ли оно "хорошим тоном" или так - понты? Также статик использую для явного приведения к базовому классу. Динамик каст использую для привидения к наследнику, а также он спасает от ошибок(попытка привести к классу которым он не является). Констант и реинтерпрет касты использую только в исключительных ситуациях, ибо если она появляется то ошибка в архитектуре и надо ее менять. Название: Re: Достоинства static_cast Отправлено: Пантер от Сентябрь 19, 2012, 21:52 констант_каст я юзаю при работе со сторонними либами с плохим апи или для снятия конста с this в константных методах. Что одно, что другое бывает достаточно редко.
реинтерпрет_каст я юзаю для чтения сишных структур из блока данных. Название: Re: Достоинства static_cast Отправлено: Akon от Сентябрь 19, 2012, 22:24 А вот такая конструкция присуща адептам const propagation (в коих числюсь и я):
Код: class ControlUnit { Название: Re: Достоинства static_cast Отправлено: Igors от Сентябрь 20, 2012, 06:41 значи я знаю, что у меня никогда не будет потерей точностей и говорю это компилятору, чтобы не сыпал варнинг... Хотя мне кажется тут на лицо, опасность, т.к. double'ы умножаются потом еще и складываются, когда-нибудь выстрел будет в ногу... поэтому если я не уверен, что (x * m.m00 + y * m.m10) и (x * m.m10 + y * m.m11) - поместится во float, я вообще не буду писать никаких приведениев ни в С++ стиле ни в Си, оставлю так, пусть компилятор говорит мне об потенциальной опасности в будущем... Влазит одинаково во float и double, опасность переполнения та же самая. Просто float будет больше терять точность т.к. умеет хранить меньше цифр - ну это забота вызывающего, если он подавал на вход float значит считал ему точности хватит.А в остальном я с Вами согласен, хотя мне больше нравится (float) или float(). Вариант "без всяких приведений" также считаю разумным, только придется запретить этот варнинг т.к. их будет очень много (это маленький кусочек показан). Остальные от ответа благоразумно уклонились и предпочитают отпихиваться общими словами - ну это их право :) Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 20, 2012, 10:22 Код
Какой смысл писать так: Код: *ioX = static_cast<float>(x * m.m00 + y * m.m10); //or in C-style (float)(x * m.m00 + y * m.m10) На счет заметности в коде вопрос спорный. Если писать функцию длиною не более 75 строк, то все преобразования заметны. Название: Re: Достоинства static_cast Отправлено: DmitryM от Сентябрь 20, 2012, 10:32 Ну, если они меняются, то константой они быть не могут (с точки зрения логики, а не возможностей языка). cv квалификаторы указывают на намерения, а не на "логику".Хотя ваш вариант сработает. |