1. C++ / Говнокод #11781

    +38

    1. 01
    2. 02
    3. 03
    4. 04
    5. 05
    6. 06
    7. 07
    8. 08
    9. 09
    10. 10
    11. 11
    12. 12
    SkinDog* crateDog()
    {
      return reinterpret_cast<SkinDog*>( new Dog() );
    };
    void deleteDog( SkinDog* pDog)
    {
      delete reinterpret_cast<Dog*>( pDog );
    }
    
    EvilDog::bite() 
    {
      Dog* pDog = mutationDog();

    Не удержался, чтоб не запостить. Сами знаете откуда.

    Запостил: LispGovno, 17 Сентября 2012

    Комментарии (81) RSS

    • ШкураСобака* ящикСобака()

      Что-за дикое ООП с reinterpret кастами?
      Ответить
      • А это как LinkedList или как его там в Java. Один класс реализует 100500 интерфейсов.
        И это называется "хорошим ооп" в "умных книжках" ;)
        Ответить
        • Пожалуйста, приведите пример "хорошей книжки", в которой говорится, что реализация классом большого количества интерфейсов считается очень хорошей практикой.

          К тому же, связный список - очень мощный и гибкий инструмент. Потому так много интерфейсов и реализует. Остальные коллекции в Java реализуют гораздо меньше интерфейсов.
          Ответить
        • > А это как LinkedList или как его там в Java. Один класс реализует 100500 интерфейсов.
          implements List<E>, Deque<E>, Cloneable, Serializable

          4 != 100500
          Ответить
          • Deque, который в свою очередь от Queue, который в свою очередь от Collection
            List, который в свою очередь от Collection
            И Collection, который в свою очередь от Iterable.

            Java is simple!
            Ответить
    • автор даже сам приветствовал публикацию здесь своего творчества
      надо было весь постить, кстати
      Ответить
      • Можно линк?
        Ответить
        • http://www.gamedev.ru/code/forum/?id=166952&page=2#m26
          Ответить
          • Спасибо.

            P.S. Мда, а автор всего лишь хотел PImpl... а ему тут такое сокрытие сбацали.
            Ответить
            • да
              но если честно, не уловил сути начальной проблемы "нихачю чтобы пользователь моего кода знал, что для работы ему понадобится windows.h"
              Ответить
              • Ну видимо, чтобы все говно из windows.h (или, как вариант, из *никсовых либ) не торчало внутрь проекта, и не лезло в интелисенс пользователю библиотеки. Все-таки там есть макросы, которые в неймспейс заэкранировать не удастся...
                Ответить
                • макросы... вспоминается только проблема с min/max, которые решаются 1) NOMINMAX в свойствах проекта или 2) способ, который мне нравится больше -
                  (std::max)(100, 200)
                  (std::min<unsigned>)('a', 95)
                  там еще что-то есть плохое?
                  Ответить
                  • > там еще что-то есть плохое?
                    ЕМНИП, всякие WORD да POINT, и почти все APIшные функции замакрены.

                    P.S. Само собой, что в крестоблядском коде мало кто захочет описать свой WORD или POINT, и проблема по большей части надумана.

                    P.P.S. А вот макрос с именем CreateFile (если мне не изменила память, и они есть) может доставить неприятности.
                    Ответить
                    • ну да, вообще на любые ansi/wide версии апишных функций у них по макросу
                      просто windows.h у меня на работе в любом виндовом проекте инклюдится прямо в pch, и не сказать, чтобы я испытывал какой-то дискомфорт
                      видать, отсутствие конфликтов имен самостоятельно разруливается использованием stl/boost стиля - я в здравом уме свою функцию CreateFile не назову
                      Ответить
                      • Зато те, кто пишут в ТакомСтиле запросто нарвутся на SetFocus() или SendMessage().

                        Поэтому против включения windows.h в проект я ничего не имею, а в либу, которую впоследствии будут юзать другие - не стоит.
                        Ответить
                • Крестопроблемы, в Дельфах нету сквозной видимости модулей.
                  Ответить
                  • эм
                    сишкопроблемы ты хотел сказать
                    все претензии только к дефайнам и любви микрософта к TCHAR (#ifdef UNICODE...), имеющей очевидное историческое обоснование
                    Ответить
                  • В крестах все кроме дефайнов (по очевидным причинам) можно загнать в неймспейс. Поэтому сишкопроблемы.
                    Ответить
                    • Мне причины не очевидны. Почему б не запилить в самом деле?
                      Ответить
                      • >Мне причины не очевидны. Почему б не запилить в самом деле?
                        Комитет не принял. Proposal на это был для С++11.
                        Ответить
                      • Дефайны относятся к текстовому препроцессору, а не к языку.
                        Можно задефайнить nsp как namespace, и писать везде nsp вместо namespace.
                        А можно препроцессировать файлы LaTeX.
                        Ответить
                        • Ну и что?
                          Ответить
                          • До препроцессирования может вообще не существовать корректного C++ кода, вот что. Может не существовать классов, структур и пространств имён.
                            Ответить
    • http://ideone.com/XgV8N
      if (auto file = std::fstream("kokoko", std::ios::in))
      {
            //...io file;
      }
      Почему не срабатывает перемещающий конструктор?
      Как видно перемещающий конструктор на месте:
      http://en.cppreference.com/w/cpp/io/basic_fstream/basic_fstream
      Ответить
      • g++ еще недопилен
        см
        http://gcc.gnu.org/onlinedocs/libstdc++/manual/status.html
        27.9	File-based streams	Partial	Missing move and swap operations
        Ответить
        • А вот написано auto file =. Неужели он не мог оптимизировать и вообще элиминировать лишние конструирования?
          Есть идеи, как переписать, чтобы работало в if уже сейчас или даже в старом стандарте?
          Ответить
          • что-нибудь объявлять прямо в if - вообще ненадёжный путь
            потому что там всё жутко ограничено
            c++03 6.4 Selection statement
            selection-statement:
                if (condition) statement
                if (condition) statement else statement
                switch (condition) statement
            condition:
                expression
                type-specifier-seq declarator = assignment-expression
            в с++11 в condition добавилась еще возможность инициализации через {}, что по сути тоже copy/move construction, а не direct
            Ответить
            • Ты понимаешь, вот так работает:
              if (std::fstream("kokoko", std::ios::in))
              {
                  
              }

              Или даже так работает:
              if (int a = (5+6))
              {
                  
              }

              Так что не понятно, почему код выше не компилируется (не считая того, что move конструктор не определен) или ещё лучше следующий код (который тоже не компилируется):
              if (std::fstream file("kokoko", std::ios::in))
              {
                    //...io file;
              }
              Ответить
              • почему не понятно
                я же всё описал
                конструктор без имени переменной - приводится к expression
                выражение с = тоже описано в стандарте
                а выражение, содержащее имя переменной и direct constructor (через скобки) - не описано
                поэтому все компиляторы его и не поддерживают
                поэтому внутри if с = будет работать, только когда заработает move ctor для ifstream
                а так - только вынос переменной до if
                Ответить
                • >а так - только вынос переменной до if
                  {
                    std::fstream file("kokoko", std::ios::in);
                    if (file)
                    {
                        //...io file;
                    }
                  }

                  Это путь по помойке. Сколько лишних конструкций приходится городить... Одни наружние {} вокруг всей конструкции стрима чего стоят...
                  В том же сишарпике все намного короче:
                  using(var file = File.Open("kokoko", FileMode.Open))
                  {
                    //... io file
                  }
                  Ответить
                  • var file = File.ReadLines("kokoko")
                    //... io file

                    Кстати, для любителей сишарпика, после чего file будет закрыт? Или уже никогда не будет, пока сборка мусора не произойдет?
                    Ответить
                    • >Или уже никогда не будет, пока сборка мусора не произойдет?
                      А с чего это ему вдруг закрываться? Пока Dispose не вызовет кто-то. Ну этот кто-то и будет GC:
                      ~FileStream ()
                      {
                      Dispose (false);
                      }

                      CLR ведь не знает - когда ты захочешь еще с этого файла что-то прочитать.
                      Другое дело, что GC может оказаться умным и если var file будет в методе, без публикации наружу, то он его соберет при выходе из этого метода.
                      Ответить
                      • > GC может оказаться умным
                        А может и не оказаться. Поэтому я не стал бы полагаться на судьбу, и закрыл бы файл самостоятельно. Неприятно будет, если программе понадобится через несколько секунд открыть файл, а гц его еще не закрыл.
                        Ответить
                  • > std::fstream file("kokoko", std::ios::in)
                    это само по себе странно, когда есть
                    std::ifstream file("kakaka");

                    а вместо скобок всегда можно сделать file.close(); в нужном месте, раз оно так жжотся, что не дотерпит до выхода из внешнего scope
                    Ответить
                  • std::fstream file("kokoko", std::ios::in);
                    if (file)
                    {
                        //...io file;
                    }
                    file.сlose();
                    Даже если я это перепишу так, то это выглядит как какое то говно без RAII. А ведь кресты славятся RAII! А оказалось, RAII в C# в данном случае выглядит лучше, чем в С++. Как же так?
                    Ответить
                    • напиши в спортлото вендорам, чтобы они уже поскорее допилили с++11, ведь без move конструктора fstream не жизнь, а пытка
                      крестотравма дает рецидив, приносит тяжкие душевные страдания
                      Ответить
            • >type-specifier-seq declarator = assignment-expression
              type-specifier-seq declarator;
              declarator=assignment-expression;

              Я правильно понял псевдокод этой конструкции?
              Получается в принципе нельзя вызвать конструктор с нужным кол-вом параметров, а только default constructor и assigment operator?
              Ответить
              • не assignment operator
                в с++ в общем случае
                type a = b;
                выполняется в последовательности
                type tmp(b);
                type a(tmp);  // copy (c++03) or copy/move(c++11) ctor

                т.е. выражение должно удовлетворять стандарту (для fstream не удовлетворяет, потому что copy ctor сокрыт, а move написать за год энтузиасты не сдюжили)
                а затем уже работает оптимизатор, который может элиминировать ненужные временные объекты

                в принципе, copy initialization vs direct initialization на ГК уже обсуждалось
                Ответить
                • >в принципе, copy initialization vs direct initialization на ГК уже обсуждалось
                  А где можно почитать и набраться уму разуму?
                  Ответить
            • Кстати, какой тег code вы использовали? А то у меня не подсвечивает слово expression и condition.
              Ответить
      • Это пиздец, этоо леденящий душу крестоблядский крестопиздец. Одна небольшая ошибка в одном месте, а кококомпилятор уже раскукарекался на 20 строчек, забрызгав нечитаемым поносом всё окно вывода. Забудешь одну букву в одном иднетификаторе, а он уже кудахчет и про то, что имени такого не знает, и что нет такого имени в таком-то пространстве имён, и что для оператора непонятно, какой тип аргумента, и ещё 20 сообщений. Я блядь если опечатаюсь или немного измению рахитектору, то блядь в этом поносе ваще нихуя не понимаю, ошибки по одной внимательно блядь разглядываю, пытаясь понять, какая же из них указывает на то, что надо, а какая - вскок просто так. И ошибки я блядь из-за этого исправляю по одной, пересобирая после каждого исправления, потому что в этом петушином поносе крестопиздоблядского кококомпилятора выделить нормально все места-источники ошибок просто невозможно.
        Ответить
      • http://ideone.com/nES2P
        if (const auto& file = std::fstream("kokoko", std::ios::in))
            {
              //...io file;
            }

        Компилится. Шо скажите посоны?
        Ответить
        • чем это отличается от
          if (std::fstream("kokoko", std::ios::in))
          Ответить
          • однако, отличается :)
            все таки ГК - полезный сайт
            с++03 и с++11: п. 12.2/5
            вкратце - в данном примере временный объект, на который ссылается ссылка, будет уничтожен только когда будет уничтожаться ссылка

            гуест (он же гумно, он же ламер007) таки заставил с++ делать using :)
            Ответить
            • Не обзывайся. Сам ламер и нуб. Языков меньше меня даже знаешь. Да и не говно я. Я LispGovno!

              Ничего я посоны не нашел. Так как пользоваться константным ссылками на файл бесполезно даже для чтения :(
              А не константная понятно не скомпилится:
              http://liveworkspace.org/code/656551e6f557ad3d34b52392679781ce


              Зато я нашел такой вариант:
              http://liveworkspace.org/code/f38b1450a08ca97e7a9013b7e8ca7df2

              if (auto&& file = std::fstream("kokoko", std::ios::in))
                  {
                    //...io file;
                  }
              Ответить
              • >auto&& file
                Этот вариант лучше auto file, тк последний предпологает вызов перемещающего конструктора, что не оптимально (Имею ввиду не конкретно файлы, а using паттерн в целом, тк он применим не только для файлов).
                Ответить
              • > Языков меньше меня даже знаешь
                Очень сильный аргумент.

                Я не боюсь того, кто изучает 10,000 различных ударов. Я боюсь того, кто изучает один удар 10,000 раз
                (с) Брюс Ли
                Ответить
              • > Так как пользоваться константным ссылками на файл бесполезно даже для чтения
                но решение так очевидно!
                http://liveworkspace.org/code/1ee1eb80806e9665c48be78d273b44cd
                Ответить
                • Не понял к чему это? Написать свою RAII обертку над std::fstream? Пользоваться const_cast? Если второе, то очевидно не пойдет. Это лишь вставка очередного костыля, который портит всю красоту кода. С ним весь код выше бессмысленен. auto&& file = подойдет лучше.

                  Мне ещё одна наркоманская мысль пришла: Написать перемещающий оператор приведения к типу? Но это пожалуй отложим до дождичка в четверг.
                  Ответить
            • >с++03
              Это не работает в старом стандарте. Хотябы из-за auto. Есть у кого идеи, как реализовать using в старом стандарте?
              Ответить
              • а не auto написать руки отсохнут?
                Ответить
                • Это долго и элегантность конструкции портит.
                  Ответить
                  • Победа!
                    using, С++, старый стандарт:
                    http://liveworkspace.org/code/bf5b986361f4b638a71cb8629ff5f584

                    #define USING(type, varName, constructorArgs) \
                       if(type& varName = const_cast<type&>(static_cast<const type&>(type constructorArgs)))
                    int main(){
                       USING(std::fstream, file, ("kokoko", std::ios::in))
                       {
                          file.ignore();
                          //...io file;
                       };
                       USING(std::fstream, file, ("kokoko1"))
                          file.gcount();
                    Ответить
                    • 1. Точка с запятой после фигурной скобки? Тарас, ты? Да, она тут потому, что
                      2. Твой макрос ломает вложенные конструкции if.
                      if (some_condition)
                          USING(...) { }
                          // WTF?! else belong to USING!
                      else {
                          do_something_else();
                      }
                      Я понимаю, что это для лулзов, но неокрепшие умы с геймдева ведь и вправду заюзают...
                      Ответить
                      • #define USING(type, varName, constructorArgs) \
                           if(false) {} else \
                           if(type& varName = const_cast<type&>(static_cast<const type&>(type constructorArgs)))
                        Так лучше?
                        Ответить
                        • Кстати, а мне нравится:
                          USING(std::fstream, file, ("kokoko", std::ios::in))
                             {
                                file.ignore();
                                //...io file;
                             }
                             else
                               std::cout<<"cant open\n";

                          http://liveworkspace.org/code/4600ad70040f6ad89187836fa2fc32f9
                          Ответить
                          • > if(false) {} else
                            > Так лучше?
                            Хм. Это никак не поможет... Плохой макрос...
                            Ответить
                            • Вообщем вот так:
                              USING(std::fstream, file, ("kokoko", std::ios::in))
                                    //...io file;
                              END_USING
                              Превратил кресты в паскаль, посему доволен. Таким образом избавлюсь от проблем рассинхронизации if else \ ; .
                              Дальше осталось сделать так бля большой паскализации:
                              #define begin { 
                              #define Begin {
                              #define bEgin {
                              ...
                              #define BEGIN {
                              Ответить
                              • Соотетственно добавлю ещё опциональный: ELSE_USING.
                                RAII снова восторжествовало!
                                Ответить
                                • #define begin { 
                                  #define Begin {
                                  #define bEgin {
                                  ...
                                  #define BEGIN {

                                  Ты меня заинтересовал. Пожалуй я перейду с дельфей на кресты.
                                  Ответить
                                  • А bEGIN-то не сработает!
                                    Ответить
                                    • почему?
                                      Ответить
                                    • > А bEGIN-то не сработает!
                                      Он спрятался за многоточием...
                                      Ответить
                                    • У меня к тебе задание:
                                      Посчитать кол-во строк в файле хедера, чтобы begin в крестах заработал также как в delphi.
                                      Ответить
                                      • > Посчитать кол-во строк в файле хедера, чтобы begin в крестах заработал также как в delphi.
                                        Учительница в школе задала тебе эту задачку? Ну уж нет, решай ее сам ;)
                                        Ответить
                                        • кстати простая задачка
                                          Ответить
                                          • > кстати простая задачка
                                            Угу. Фактически в одно действие.
                                            Ответить
                                            • Нет, мы битосдвиги не проходили. Задачка решается циклом.
                                              Ответить
    • Существуют ли в мире одинаковые люди или очень похожие душой?
      Ответить

    Добавить комментарий