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

    +7

    1. 01
    2. 02
    3. 03
    4. 04
    5. 05
    6. 06
    7. 07
    8. 08
    9. 09
    10. 10
    11. 11
    12. 12
    13. 13
    14. 14
    15. 15
    16. 16
    17. 17
    18. 18
    19. 19
    #include <iostream>
    
    using namespace std;
    
    class Foo {
    public:
        operator int() const {
            cout<<"1";
            return *this;
        }
    };
    
    int main() {
        Foo foo;
        int i = foo;
    
        cout<<i<<endl;
        return 0;
    }

    Запостил: govnokod3r, 28 Апреля 2016

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

    • порадовало что даже с -O1, g++ разворачивает уже даже рекурсивные "циклы":
      0000000000400960 <Foo::operator int() const>:
        400960:       53                      push   %rbx
        400961:       48 89 fb                mov    %rdi,%rbx
        400964:       ba 01 00 00 00          mov    $0x1,%edx
        400969:       be b4 0a 40 00          mov    $0x400ab4,%esi
        40096e:       bf 80 10 60 00          mov    $0x601080,%edi
        400973:       e8 78 fe ff ff          callq  4007f0 <std::basic_ostream<char, std::char_traits<char> >& std::__ostream_insert<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*, long)@plt>
        ; ... 6 of the same blocks skipped ...
        400a04:       ba 01 00 00 00          mov    $0x1,%edx
        400a09:       be b4 0a 40 00          mov    $0x400ab4,%esi
        400a0e:       bf 80 10 60 00          mov    $0x601080,%edi
        400a13:       e8 d8 fd ff ff          callq  4007f0 <std::basic_ostream<char, std::char_traits<char> >& std::__ostream_insert<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*, long)@plt>
        400a18:       48 89 df                mov    %rbx,%rdi
        400a1b:       e8 40 ff ff ff          callq  400960 <Foo::operator int() const>
        400a20:       5b                      pop    %rbx
        400a21:       c3                      retq

      почти тэйл рукурсия в крестах. кто бы мог подумать.

      ЗЫ и самое крутое что побочный эффект бесконечной рекурсии сохранен! (== переполнение стэка.) улучшили производительность - печатаем больше копеек - и одновременно мы делаем это "быстрее" потому что "цикл" развернули.
      Ответить
      • Известно, что переход на C++ позволяет выполнить бесконечный цикл в два раза быстрее.
        Ответить
    • При чём тут cout <<i<<endl ?
      Ответить
      • Некоторые веруют, что в конце бесконечного цикла наступит '\n'. Хотя на самом деле там будет eof.
        Ответить
      • чтобы при компиляции ворнинга не было
        Ответить
    • int recursion {
         return recursion();
      }
      Ответить
      • Это перл?
        Ответить
        • Пишу с утюга.
          У меня "int" заменяется на "isn't"
          Ответить
          • Охблядь, как меня заебал этот утюг со своей автозаменой, сука. Ее даже отключить нельзя.
            Ответить
    • рекурсия в перегруженных операторах - самая веселая часть плюсов.
      Ответить
      • bool operator == (const T& other) {
            return !(*this != other);
        }
        bool operator != (const T& other) {
            return !(*this == other);
        }
        Ответить
        • это еще легко заметить. А вот когда у тебя типы преобразуются туда-сюда то через implicit constructor, то через operator type, уже и не поймешь, развернется t == 5 в operator == (T l, T r) или в built-in оператор сравнения интов. UB с потенциальной бесконечной рекурсией. Ляпота...
          Ответить
    • А gcc 5.3 с -O2 выпилил вообще весь Foo КЕМ и оставил только вечный цикл:
      .LC0:
              .string "1"
      main:
              sub     rsp, 8
      .L2:
              mov     edx, 1
              mov     esi, OFFSET FLAT:.LC0
              mov     edi, OFFSET FLAT:std::cout
              call    std::basic_ostream<char, std::char_traits<char> >& std::__ostream_insert<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*, long)
              jmp     .L2
              sub     rsp, 8
              mov     edi, OFFSET FLAT:std::__ioinit
              call    std::ios_base::Init::Init()
              mov     edx, OFFSET FLAT:__dso_handle
              mov     esi, OFFSET FLAT:std::__ioinit
              mov     edi, OFFSET FLAT:std::ios_base::Init::~Init()
              add     rsp, 8
              jmp     __cxa_atexit
      Ответить

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