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

    −11

    1. 1
    pow(2.0, n)

    Запостил: 3_dar, 10 Сентября 2015

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

    • наверное, если бы можно было обойтись сдвигом, написали бы 2 вместо 2.0?
      Ответить
      • А почему нельзя обойтись сдвигом?
        Ответить
        • Может быть, потому что n - это double?
          Ответить
          • Такие мелочи не остановят истинного байтоёба: http://ideone.com/2iY5co
            Ответить
            • Чо это за хак?
              Ответить
              • 1. Число представлено как (Знак,Мантисса,Экспонента) = З * М * 2^Э, по нескольку (см. стандарты плавающих питухов) бит на каждый кусок.
                2. union позволяет обращаться к одному и тому же куску памяти как к переменным с разными типами данных. В данном случае double интерпретируется как int64 и наоборот.
                3. Борманд формирует такое целое число, которое соответствует требуемой степени двойки и пишет его напрямую в экспоненту, сдвигая на размер мантиссы.
                4. Первая цифра мантиссы всегда единица, потому игнорируется, следовательно, 52 нуля означают единицу.
                Ответить
                • Ахаха теперь понял. Да, это, конечно, элитно - копировать степень в экпоненту. А теперь тоже самое для происвольного основания.
                  Ответить
                  • > А теперь тоже самое для происвольного основания.
                    Только если ты покажешь, как сдвигами возвести произвольное целое число в произвольную степень ;)

                    Понятно, что эти хаки работают только для степеней двойки.
                    Ответить
                    • Через логарифм же. Правда, по времени получится так же.
                      Ответить
            • Эээє? У Вас система исчисления отклеилась..
              printf("%f\n", pow2(0)); // 1.000000
                  printf("%f\n", pow2(1)); // 2.000000
                  printf("%f\n", pow2(32)); // 4294967296.000000
                  printf("%f\n", pow2(64)); // 18446744073709551616.000000
                  printf("%f\n", pow2(-1)); // 0.500000
                  printf("%f\n", pow2(-2)); // 0.250000
              Ответить
            • А компилятор это не сворачивает?
              Ответить
              • > сворачивает
                Во что?
                Ответить
                • в плане "не оптимизирует ли компилятор операции возведения в степень чисел-степеней двойки"
                  Ответить
                  • в даблах-то? нет
                    разве что подставит конечное значение, если во время компиляции будут известны все аргументы
                    Ответить
            • Потому что ЭН это доубле, а не результат.
              Давай, возведи двойку в степень 0.5
              Ответить
          • В чем тогда говнокод?
            Ответить
        • Потому что автора кода в школе не учили умножать сдвигами.
          Ответить
          • Но тут не умножение, а возведение в степень.
            Ответить
      • Очень часто вижу
        for(i = 0; i < pow(2, n); i++)
        Ответить
      • Не все компиляторы понимают pow(2, n), если n - int
        Ответить

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