Skip to content

Instantly share code, notes, and snippets.

@vk26
Last active September 15, 2015 14:23
Show Gist options
  • Select an option

  • Save vk26/c93f1927740190171ae5 to your computer and use it in GitHub Desktop.

Select an option

Save vk26/c93f1927740190171ae5 to your computer and use it in GitHub Desktop.
Поиск 2 пропущенных элементов отсортированного массива. Двумя способами: через бинарный поиск и через побитовые операции.
require 'byebug'
require 'wrong/assert'
require "benchmark/ips"
include Wrong::Assert
module Search
def get_bit(num, bit = 1)
unless num & bit == 0
return bit
else
get_bit num, bit * 2
end
end
def search_xor(arr, n)
z = [*0..n].inject { |s, a| arr[a].nil? ? s ^ a : s ^ a ^ arr[a] }
b = get_bit(z)
x = [*0..n].select{|a| a & b > 0}.reduce(:^) ^ arr.select{|a| a & b > 0}.reduce(:^)
y = z ^ x
[x, y].sort
end
def binary_search(arr, first = 0, last = 0, solution = [])
return solution.sort if solution.count == 2
last = arr.count if last.zero?
m = (last - first)/2 + first
if arr[m] == m + 2 #left
if arr[m-1] == m - 1
solution << m << m + 1
elsif arr[m-1] == m
solution << m + 1
else
binary_search arr, first, m, solution
end
elsif arr[m] == m + 1 #left + right
if arr[m-1] == m - 1
solution << m
else
binary_search arr, first, m, solution
end
if arr[m+1] == m + 3
solution << m + 2
else
binary_search arr, m, last, solution
end
elsif arr[m] == m #right
if arr[m+1] == m + 3
solution << m + 1 << m + 2
elsif arr[m+1] == m + 2
solution << m + 1
else
binary_search arr, m, last, solution
end
end
end
end
include Search
arr1 = [*0..11] + [*13..15] + [*17..20]
solution = binary_search(arr1)
assert { solution == [12, 16] }
solution = search_xor(arr1, 20)
assert { solution == [12, 16] }
arr2 = [*0..11] + [*14..20]
solution = binary_search(arr2)
assert { solution == [12, 13] }
solution = search_xor(arr2, 20)
assert { solution == [12, 13] }
Benchmark.ips do |x|
x.report("binary search") { binary_search(arr1) }
x.report("search xor") { search_xor(arr1, 20) }
x.compare!
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment