Re: new new challenge

new topic     » goto parent     » topic index » view thread      » older message » newer message

> This is a new and (I think) simpler challenge:
> Find the fastest algorithm to compute the largest power of 2 that
exactly
> divides an integer from 1 to 2^31 - 1.

Hi,
The solution boils down to finding the value of the least significant
bit.
Here are two alternatives... unfortunately the ugly one is faster.
Ross


-- This solution is elegant but slower due to the divide by 2.
-- If Euphoria had a bit shift operator or integer division
-- this would probably be the fastest method.

function best2(integer x)
    if and_bits(x,1) then  -- quickly eliminate odd numbers
        return 1
    end if
    return floor(xor_bits(x,x-1)/2) + 1
end function

-- Cruder and faster solution...
-- You could make it even faster by 'jumping' depending on the
-- value of x and hence reduce the number of comparisons.
-- But why bother... this method stinks already.
function best(integer x)
    if and_bits(x,1) then
        return 1
    end if
    if and_bits(x,2) then
        return 2
    end if
    if and_bits(x,4) then
        return 4
    end if
    if and_bits(x,8) then
        return 8
    end if
    if and_bits(x,16) then
        return 16
    end if
    if and_bits(x,32) then
        return 32
    end if
    if and_bits(x,64) then
        return 64
    end if
    if and_bits(x,128) then
        return 128
    end if
    if and_bits(x,256) then
        return 256
    end if
    if and_bits(x,512) then
        return 512
    end if
    if and_bits(x,1024) then
        return 1024
    end if
    if and_bits(x,2048) then
        return 2048
    end if
    if and_bits(x,4096) then
        return 4096
    end if
    if and_bits(x,8192) then
        return 8192
    end if
    if and_bits(x,16384) then
        return 16384
    end if
    if and_bits(x,32768) then
        return 32768
    end if
    if and_bits(x,65536) then
        return 65536
    end if
    if and_bits(x,131072) then
        return 131072
    end if
    if and_bits(x,262144) then
        return 262144
    end if
    if and_bits(x,524288) then
        return 524288
    end if
    if and_bits(x,1048576) then
        return 1048576
    end if
    if and_bits(x,2097152) then
        return 2097152
    end if
    if and_bits(x,4194304) then
        return 4194304
    end if
    if and_bits(x,8388608) then
        return 8388608
    end if
    if and_bits(x,16777216) then
        return 16777216
    end if
    if and_bits(x,33554432) then
        return 33554432
    end if
    if and_bits(x,67108864) then
        return 67108864
    end if
    if and_bits(x,134217728) then
        return 134217728
    end if
    if and_bits(x,268435456) then
        return 268435456
    end if
    if and_bits(x,536870912) then
        return 536870912
    end if
    if and_bits(x,1073741824) then
        return 1073741824
    end if
    return 0
end function

procedure test(integer iter, integer top)
    integer n, k
    atom sum, t0, t1
    sum = 0
    for i = 1 to top do
        for j = 0 to 31 do
            n = power(2, j)
            if remainder(i,n) != 0 then
                exit
            end if
        end for
        n = n / 2
        t1 = time()
        for j = 1 to iter do
            k = dummy(i)
        end for
        t1 = time() - t1
        t0 = time()
        for j = 1 to iter do
            k = best(i)
        end for
        sum += time() - t0 - t1
        if n != k then
            printf(1, "%s %d %s %d \n", {"Error! ", n, "not equal", k})
        end if
    end for
    printf(1, "%s %f \n", {"Time:", sum})
end procedure

test(100000, 100)

if wait_key() then end if

new topic     » goto parent     » topic index » view thread      » older message » newer message

Search



Quick Links

User menu

Not signed in.

Misc Menu