Няшная / Говнокод #11847 Ссылка на оригинал

0

  1. 1
  2. 2
  3. 3
  4. 4
  5. 5
  6. 6
  7. 7
  8. 8
  9. 9
  10. 10
  11. 11
  12. 12
  13. 13
  14. 14
  15. 15
  16. 16
  17. 17
  18. 18
#include <stdio.h>

void swap(long *a,long *b){
  *a=(*a<<sizeof(*a)*4);
  *a+=*b;
  *b=*a ^ *b;
  *b=(*b>>sizeof(*a)*4);
  *a=(*a<<sizeof(*a)*4);
  *a=(*a>>sizeof(*a)*4);
}

int main(){
 long a=22807;
 long b=1012;
   printf("a=%ld b=%ld\n",a,b);
 swap(&a,&b);
  printf("a=%ld b=%ld\n",a,b);
}

Swap variables without third variable

Запостил: AliceGoth AliceGoth, (Updated )

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

  • http://ideone.com/eCVss
    FAIL. (т.к. нормально обменивает только числа в половину разрядности long'а).

    P.S. Но реализация понравилась, такого извращения для обмена переменных я еще не видел, поэтому ловите плюс.
    Ответить
    • > long a=22807;
      > long b=1012;
      Автора сгубило неумение писать юнит-тесты
      Ответить
      • > Автора сгубило неумение писать юнит-тесты
        Что вы, это наоборот умение "как составить тесты для неработоспособной программы, чтобы сдать ее неопытному заказчику".
        Ответить
      • Что то такое?

        long long int a=-41000L;
        long long int b=-5305L;
        for(long i=0;i<=1000000L;i++){
        printf("before a=%lld b=%lld\n",a,b);
        swap(&a,&b);
        printf("after a=%lld b=%lld\n",a,b);
        swap(&a,&b);
        printf("a=%ld b=%ld\n",a,b);
        a++;b++;
        }
        Ответить
        • > long long int;
          Тогда, чтобы быть честным, запилите цикл до 4000000000 (можно с большим шагом). Баг с потерей старших разрядов один хрен не устранен.

          > printf("after a=%lld b=%lld\n",a,b);
          Юнит-тест не должен лишний раз показывать промежуточные результаты (разве что если найдет ошибку), а должен показывать результат теста - успех или ошибку. К примеру:
          long long tmpa = a, tmpb = b;
          swap(tmpa, tmpb);
          if (tmpa != b || tmpb != a) {
              printf("Test failed on a=%lld b=%lld\n", a, b);
              return 1;
          }
          Ответить
  • Знак теряется если одна <0, то вычитается из числа
    более правильно
    #include <stdio.h>

    void swap(int *a,int *b){
    if(*a<0 & *b<0){
    *a*=-1;*b*=-1;
    *a=(*a<<sizeof(*a)*4);
    *a+=*b;
    *b=*a ^ *b;
    *b=(*b>>sizeof(*a)*4);
    *a=(*a<<sizeof(*a)*4);
    *a=(*a>>sizeof(*a)*4);
    *a*=-1;*b*=-1;
    } else if(*a<0){
    *a*=-1;
    *a=(*a<<sizeof(*a)*4);
    *a+=*b;
    *b=*a ^ *b;
    *b=(*b>>sizeof(*a)*4);
    *a=(*a<<sizeof(*a)*4);
    *a=(*a>>sizeof(*a)*4);
    *b*=-1;
    } else if(*b<0){
    *b*=-1;
    *a=(*a<<sizeof(*a)*4);
    *a+=*b;
    *b=*a ^ *b;
    *b=(*b>>sizeof(*a)*4);
    *a=(*a<<sizeof(*a)*4);
    *a=(*a>>sizeof(*a)*4);
    *a*=-1;
    } else {
    *a=(*a<<sizeof(*a)*4);
    *a+=*b;
    *b=*a ^ *b;
    *b=(*b>>sizeof(*a)*4);
    *a=(*a<<sizeof(*a)*4);
    *a=(*a>>sizeof(*a)*4);
    }
    }
    Ответить
    • > Знак теряется
      Да тут не только знак, тут в строке 4 половина разрядов числа a втопку уходит: *a=(*a<<sizeof(*a)*4). Новый вариант в этом плане ничуть не лучше.

      > *a*=-1
      Красота 😉
      Ответить
        • А вот такой код не требует, и работает на полную разрядность переменных:
          *a ^= *b;
          *b ^= *a;
          *a ^= *b;
          Ответить
            • Фу-у. Так оно даже не будет работать в языках с нормальным приоритетом.
              tmp1 = a; 
               tmp2 = b;
               tmp3 = a ^ b;	//=a^b
              a = tmp3;	//=a^b
              b = tmp2 ^ tmp3;//=(b) ^ (a^b) =a
              a = tmp1 ^ b; 	//=a^a=0

              Рекомендую сравнить по количеству действий с тем как пишут "тупые", неилитарные кодеры.
              tmp = a;
              a=b;
              b=tmp;
              Ответить
              • > как пишут "тупые", неилитарные кодеры
                А "умные" неилитарные кодеры пишут swap(a, b)
                Ответить
                      • Nemerle, ага. Самое бесполезное, что есть в Немерле. Но таки в этом действительно всех уделал по интуитивности и краткости.
                        Ответить
                    • Это какой-то выдуманный сверхлаконичный язык был, весёлая тема была на рдсн.
                      Чувак показал пример сортировки пузырьком на своём языке:
                      a[i]>a[j]?a[i]:=:a[j]

                      правда неоднозначность семантики выяснилась слишком быстро.
                      Ответить
              • Фууу, тмп, это же так по-ламерски. Настоящий кулхацкер, знающий железо, никогда так не напишет.
                Ответить
                  • на register компилятор, насколько я помню, давно уже плюет с высокой колокольни.
                    а с auto тоже смысл изменился из C++0x.
                    Ответить
                    • >а с auto тоже смысл изменился из C++0x.
                      Если вы не заметили, то этот новый смысл как раз применяется.

                      >на register компилятор, насколько я помню, давно уже плюет с высокой колокольни.
                      Эх, надо было мне код зеленым оборачивать.
                      Ответить
          • Только почему-то никто никогда не говорит, что этот "умный" код полное говно. Потому что оно медленее чем обычная перестановка с лишней переменной.
            Даже в былые времена когда регистров было мало, это считалось сомнительным ибо существовал XCHG.
            Ответить
            • > это считалось сомнительным
              Это же просто головоломка. Зачем к ней так серьезно подходить?

              P.S. То что говно - да. И к тому же (по крайней мере на x86) компилятор запилит временную переменную в регистре (если сами a и b не в регистрах), т.к. на x86 нельзя выполнять операции над двумя областями памяти одной командой.
              Ответить
              • Если a и b оказались в памяти какого-то хера, то палюбэ пизда скорости, и да, сишкобляская передача по указателю способствует.
                А если они в регистрах, то обмен скорее всего будет в 3 действия через третий регистр.
                Ответить
                • Я не о скорости, я о том что сишкоблядский некристекомпилятор может нарушить условие задачи, создав временную переменную, тем самым поставив данное решение под сомнение.
                  Ответить
  • Вызвало ассоциации с наряженной елкой.. наверно программист спешил домой 31 декабря =)
    Ответить

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

Помни, guest, за тобой могут следить!

    А не использовать ли нам bbcode?


    8