1. Си / Говнокод #20003

    −47

    1. 1
    2. 2
    3. 3
    4. 4
    int cmpfunc (const void * a, const void * b)
    {
       return ( *(int*)a - *(int*)b );
    }

    в догонку к http://govnokod.ru/19968
    http://www.tutorialspoint.com/c_standard_library/c_function_qsort.htm
    Переполнение знаковых целых чисел - не, не слышал

    Запостил: j123123, 14 Мая 2016

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

    • притом особенно гадко, что это пример из туториала
      Ответить
      • Это же пример учебный. Он предназначен для того, чтобы читатель учился искать ошибки.
        Ответить
        • А если читатель не поймет авторского замысла, и решит что это пример хорошего кода, который 100% корректно работает для всех допустимых входных массивов из int?
          Ответить
          • пусть читатель тогда не читает всякую хуйню не понятно от куда.

            А то иш, если с колокольни поп сказал, значит надо в это верить.
            Ответить
    • Так а если у человека по определению не могут быть большие числа. И что теперь? INT_MAX и INT_MIN туда пихать?
      Ответить
      • Да. Иначе не получишь сертификацию от ФСБ, Министерства обороны, Гостехнадзора, Роспотребнадзора и от Эльвиры Сахипзадовны Набиуллиной.
        Ответить
      • По какому такому определению? Там разве сказано, что "этот пример будет работать только если у вас там числа лежат в таком-то интервале"? Нет, нихрена такого там не сказано. Вот тут например
        return ( *(int*)a - *(int*)b );

        http://melpon.org/wandbox/permlink/O2t478eLe4szylSV - НЕВЫРОВНЕННОСТЬ УКАЗАТЕЛЕЙ вполне возможна, если например сортируем какой-нибудь массив из структур, которые плотно упакованы. Таким образом, указатель на int может быть не кратен 4 (если у нас 4-байтный инт) и на некоторых архитектурах будет жопа. Так что эту поебень надо заменить на memcpy, вот так:
        int va, vb;
        memcpy(&va, a, sizeof(va));
        memcpy(&vb, b, sizeof(vb));

        При вычитании там может переполнится в минусах, это будет во-первых UB, а во-вторых даже если бы это было не UB (т.е. если б отняв единицу от INT_MIN мы б по стандарту получили бы значение INT_MAX и чтобы стандартом было закреплено что тут точно two's complement используется) то получилась бы все равно хуита, например такое сравнение INT_MIN с единицей показало бы, что единица МЕНЬШЕ чем INT_MIN, что естественно является полнейшей хуитой. Таким образом, надо сделать:
        if (va >v b) return 1;
        if (va < vb) return -1;
        return 0;

        или
        return (va > vb)-(va < vb)
        Ответить
        • > return (va > vb)-(va < vb)
          Не надо так делать, пожалей читателей...
          Ответить
          • Почему нет? gcc на нем меньше инструкций генерирует https://godbolt.org/g/1eb0iZ
            Это ж мое фирменное изобретение, придуманное в http://govnokod.ru/19968
            Ответить
          • А что не так?
            Ответить
          • А в Паскале пришлось бы писать ord(va > vb) - ord(va < vb) и всем было бы ясно, что в выражении происходит каст була в инт. Ох уж эта сишка с неявными кастами...
            Ответить
            • Булин - на страже сгущенки
              http://dump.bitcheese.net/files/pulikej/Яша_учится_программировать1.6.jpg
              http://www.programmingforkids.ru/2013/09/o-knige-dlya-detei.html
              Ответить
              • А про плавающих питухов там ничего нет?
                Ответить
                • Монстрики-переменные из семейства float
                  страница 173
                  Ответить
                  • Они там учат плохому:
                    myColor = (int)random(255);
                    вместо более явных функций floor и ceil.

                    А также учат экмаблядству вроде сложения строк с числами:
                    "девочка Ляля вчера хохотала " + 5 + " раз"


                    То ли дело "PHP":
                    "девочка Ляля вчера хохотала " . strval(5) . " раз"
                    Ответить
                    • то ли дело питон
                      >>> 'hui '*3
                      'hui hui hui '
                      Ответить
                      • Да! В Питоне хотя бы логично: отсутствует сложение величин разной размерности. Ещё бы деление ввести:
                        >>> 'hui hui hui '/3
                        'hui '
                        Ответить
                        • 'hui' / 3
                          Ответить
                          • Напоминает анекдот про школьника с лопатой, который пытался найти в земле квадратный корень, и про школьника с ножом...
                            Ответить
                            • Для тех кто вдруг его не знает:

                              - Саша, ты что делаешь?
                              - Дерево выкапываю, математичка домашку дала - корень найти.
                              - Ни фига, тебе ещё повезло: Федьке она ваще сказала член на многочлен разделить. Сидит, нож точит, плачет.
                              Ответить
                        • чему тогда будет равно
                          >>> 'hui hui hui hui '/3

                          или
                          >>> 'govno govno hui '/3

                          ?
                          Ответить
                          • "hui h" и "govno" соответственно

                            Предлагаю для s, n: typeof s === 'string', typeof n === number, n >= 0, (n | 0) === n следующее определение: div = (s, n) => s.substring(0, s.length / n);
                            Ответить
                            • Как вариант - можно в / вернуть ["hui h", "ui hu", "i hui"], а в % - " ".
                              Ответить
                              • И даже смысл в этом есть: можно парсить таблицы.
                                P.S. Таблицы с равной шириной/длиной
                                Ответить
                          • 'hui h' и 'govno' соответственно

                            Блин, 1024-- опередил

                            > s.substring(0, s.length / n);
                            Да, я так и считал.
                            Ответить
                    • А я раньше думал что "ляля" + 5 будет NaN
                      Ответить
                • >>сгущенки
                  >>петухов

                  на зоне чалился?
                  Ответить
        • Можешь объяснить, зачем мемцпу? При чем тут упакованные структуры, если по той ссылке сортируют массив интов? При чем тут вообще структуры?
          Ответить
          • memcpy чтоб можно было сравнивать по невыровненным указателям. Упакованные структуры тут притом, что если эту функцию попробовать использовать для сравнения интов по указателям, взятым из упакованных структур (т.е. если мы будем сортировать массив из упакованных структур по int в них, и он будет не всегда выровнен по границе 4 байт) то надо вытаскивать int из указателя через memcpy а не таким вот прямым разыменованием
            Ответить
            • А зачем из функции сравнения структур вызывать функцию сравнения чисел?
              Кстати, как вообще работают с такими структурами на таких нехороших архитектурах? Чтобы достать поле, его (неявно) побайтово копируют куда-то?
              Ответить
              • Ну например если надо сортировать массив из int внутри стуктуры, который не кратен 4.
                Если же передавать адреса структур и потом из них извлекать через -> то вроде как никаких проблем быть не должно
                Ответить
            • Вывод - нехуй сортировать массивы из неупакованных структур.
              Ответить
              • Может как раз таки из упакованных? Ведь именно в плотноупакованных структурах возможна такая жопа
                Ответить
                • Тьфу, да. Хотел сказать "невыровненных". Имхо, упакованные структуры нужны только для сериализации. Внутри программы им делать нехуй.
                  Ответить
                  • ну это пока ОЗУ хватает
                    Ответить
                    • > ОЗУ хватает
                      Если из-за нехватки ОЗУ приходится ломать alignment полей в структурах... То это уже embedded какой-то.
                      Ответить
            • Какие-то искусственные проблемы ты изобретаешь. Так и скажи, что хотел доебаться.
              Ответить

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