algorithmable 0.13.0 → 0.14.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +1 -1
- data/algorithmable.gemspec +1 -0
- data/lib/algorithmable/cache/imp.rb +19 -0
- data/lib/algorithmable/cache/primitive_max_heap.rb +38 -0
- data/lib/algorithmable/cache/primitive_min_heap.rb +38 -0
- data/lib/algorithmable/cache.rb +15 -0
- data/lib/algorithmable/cups/circular_dependencies.rb +27 -0
- data/lib/algorithmable/cups/longest_common_subsequence.rb +46 -0
- data/lib/algorithmable/cups/merge_two_arrays.rb +31 -0
- data/lib/algorithmable/cups/nested_lists_problem.rb +105 -0
- data/lib/algorithmable/cups/number_of_occurrences_in_array.rb +49 -0
- data/lib/algorithmable/cups/primitives.rb +205 -2
- data/lib/algorithmable/cups/root_cube_issue.rb +39 -0
- data/lib/algorithmable/cups/stacks_and_queues/stack_sorter.rb +25 -0
- data/lib/algorithmable/cups/stacks_and_queues/stack_with_min.rb +23 -0
- data/lib/algorithmable/cups/stacks_and_queues/towers_of_hanoi.rb +48 -0
- data/lib/algorithmable/cups/stacks_and_queues/triple_stack.rb +52 -0
- data/lib/algorithmable/cups/stacks_and_queues/two_stacks_queue.rb +37 -0
- data/lib/algorithmable/cups/stacks_and_queues.rb +31 -0
- data/lib/algorithmable/cups/stocks.rb +80 -0
- data/lib/algorithmable/cups/task_shedule_with_coldtime.rb +16 -0
- data/lib/algorithmable/cups/two_sum.rb +59 -0
- data/lib/algorithmable/cups.rb +7 -0
- data/lib/algorithmable/data_structs/linked_list/base.rb +21 -1
- data/lib/algorithmable/data_structs/linked_list/doubly.rb +1 -1
- data/lib/algorithmable/data_structs/linked_list/singly.rb +62 -1
- data/lib/algorithmable/data_structs/queue.rb +4 -0
- data/lib/algorithmable/data_structs/stack.rb +4 -0
- data/lib/algorithmable/data_structs/tree/binary.rb +10 -0
- data/lib/algorithmable/data_structs/tree/binary_search.rb +206 -0
- data/lib/algorithmable/data_structs/tree.rb +13 -0
- data/lib/algorithmable/data_structs.rb +6 -0
- data/lib/algorithmable/sort/bubble.rb +9 -16
- data/lib/algorithmable/sort/insertion.rb +24 -0
- data/lib/algorithmable/sort/merge.rb +4 -8
- data/lib/algorithmable/sort/quick_sort.rb +35 -0
- data/lib/algorithmable/sort/selection.rb +23 -0
- data/lib/algorithmable/sort/shell.rb +27 -0
- data/lib/algorithmable/sort/shuffle.rb +15 -0
- data/lib/algorithmable/sort/utils.rb +66 -0
- data/lib/algorithmable/sort.rb +28 -0
- data/lib/algorithmable/union_find.rb +51 -0
- data/lib/algorithmable/version.rb +1 -1
- data/lib/algorithmable.rb +2 -0
- data/script/benchmarks/sort.rb +37 -0
- metadata +46 -2
@@ -0,0 +1,35 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module Sort
|
3
|
+
class QuickSort
|
4
|
+
extend Algorithmable::Sort::Utils
|
5
|
+
|
6
|
+
def self.sort(collection)
|
7
|
+
do_effect(collection, 0, collection.length - 1)
|
8
|
+
end
|
9
|
+
|
10
|
+
private
|
11
|
+
|
12
|
+
def self.do_effect(collection, lo, hi)
|
13
|
+
return collection if hi <= lo
|
14
|
+
lo_or_hi = partition(collection, lo, hi)
|
15
|
+
do_effect(collection, lo, lo_or_hi - 1)
|
16
|
+
do_effect(collection, lo_or_hi + 1, hi)
|
17
|
+
end
|
18
|
+
|
19
|
+
# private
|
20
|
+
#
|
21
|
+
# def self.partition(ary, from, to)
|
22
|
+
# pivot = ary[from]
|
23
|
+
# i = from + 1
|
24
|
+
# (from + 1).upto(to).each do |j|
|
25
|
+
# if ary[j] < pivot
|
26
|
+
# ary[i], ary[j] = ary[j], ary[i]
|
27
|
+
# i += 1
|
28
|
+
# end
|
29
|
+
# end
|
30
|
+
# ary[i-1], ary[from] = ary[from], ary[i-1]
|
31
|
+
# i
|
32
|
+
# end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module Sort
|
3
|
+
class Selection
|
4
|
+
extend Algorithmable::Sort::Utils
|
5
|
+
# Does sorting in O(n2) time (quadratic time)
|
6
|
+
#
|
7
|
+
def self.sort(collection)
|
8
|
+
return collection if collection.empty? || 1 >= collection.length
|
9
|
+
length = collection.length - 1
|
10
|
+
|
11
|
+
0.upto(length).each do |i|
|
12
|
+
min = i
|
13
|
+
(1 + i).upto(length).each do |j|
|
14
|
+
min = j if collection[j] < collection[min]
|
15
|
+
end
|
16
|
+
exchange(i, min, collection)
|
17
|
+
end
|
18
|
+
|
19
|
+
collection
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module Sort
|
3
|
+
class Shell
|
4
|
+
extend Algorithmable::Sort::Utils
|
5
|
+
def self.sort(collection)
|
6
|
+
return collection if 2 > collection.length
|
7
|
+
length = collection.length
|
8
|
+
h = 1
|
9
|
+
|
10
|
+
h = 3 * h + 1 while h < length / 3
|
11
|
+
|
12
|
+
while h >= 1
|
13
|
+
h.upto(length - 1).each do |i|
|
14
|
+
j = i
|
15
|
+
while j >= h && collection[j] < collection[j - h]
|
16
|
+
exchange(j, j - h, collection)
|
17
|
+
j -= h
|
18
|
+
end
|
19
|
+
end
|
20
|
+
h /= 3
|
21
|
+
end
|
22
|
+
|
23
|
+
collection
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module Sort
|
3
|
+
class Shuffle
|
4
|
+
extend Algorithmable::Sort::Utils
|
5
|
+
|
6
|
+
def self.sort(collection)
|
7
|
+
return collection if collection.empty? || 2 > collection.length
|
8
|
+
collection.length.times do |i|
|
9
|
+
exchange(i, rand(i + 1), collection)
|
10
|
+
end
|
11
|
+
collection
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module Sort
|
3
|
+
module Utils
|
4
|
+
# @param [Integer] a
|
5
|
+
# @param [Integer] bottom
|
6
|
+
# @param [Array] top
|
7
|
+
# @return [Integer] Integer representing new pivot location
|
8
|
+
def partition(a, bottom, top)
|
9
|
+
i = bottom
|
10
|
+
j = top.succ
|
11
|
+
v = a[bottom]
|
12
|
+
loop do
|
13
|
+
while a[i += 1] < v
|
14
|
+
break if i == top
|
15
|
+
end
|
16
|
+
while v < a[j -= 1]
|
17
|
+
break if j == bottom
|
18
|
+
end
|
19
|
+
break if i >= j
|
20
|
+
cur_i = a[i]
|
21
|
+
a[i] = a[j]
|
22
|
+
a[j] = cur_i
|
23
|
+
end
|
24
|
+
cur_bottom = a[bottom]
|
25
|
+
a[bottom] = a[j]
|
26
|
+
a[j] = cur_bottom
|
27
|
+
j
|
28
|
+
end
|
29
|
+
|
30
|
+
# def partition(ary, from, to)
|
31
|
+
# pivot = ary[from]
|
32
|
+
# i = from + 1
|
33
|
+
# (from + 1).upto(to).each do |j|
|
34
|
+
# if ary[j] < pivot
|
35
|
+
# ary[i], ary[j] = ary[j], ary[i]
|
36
|
+
# i += 1
|
37
|
+
# end
|
38
|
+
# end
|
39
|
+
# ary[i-1], ary[from] = ary[from], ary[i-1]
|
40
|
+
# i
|
41
|
+
# end
|
42
|
+
|
43
|
+
# @param [Integer] from
|
44
|
+
# @param [Integer] to
|
45
|
+
# @param [Array] collection
|
46
|
+
# @return [Object]
|
47
|
+
def exchange(from, to, collection)
|
48
|
+
return collection if from == to
|
49
|
+
local_from = collection[from]
|
50
|
+
collection[from] = collection[to]
|
51
|
+
collection[to] = local_from
|
52
|
+
collection
|
53
|
+
end
|
54
|
+
|
55
|
+
# @param [Integer] collection
|
56
|
+
# @param [Integer] i
|
57
|
+
# @return [Array] collection
|
58
|
+
def swap(collection, i)
|
59
|
+
current = collection[i]
|
60
|
+
collection[i] = collection[i + 1]
|
61
|
+
collection[i + 1] = current
|
62
|
+
collection
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
data/lib/algorithmable/sort.rb
CHANGED
@@ -1,10 +1,22 @@
|
|
1
1
|
module Algorithmable
|
2
2
|
module Sort
|
3
|
+
autoload :Utils, 'algorithmable/sort/utils'
|
4
|
+
autoload :Selection, 'algorithmable/sort/selection'
|
5
|
+
autoload :Insertion, 'algorithmable/sort/insertion'
|
6
|
+
autoload :Shell, 'algorithmable/sort/shell'
|
7
|
+
autoload :Shuffle, 'algorithmable/sort/shuffle'
|
3
8
|
autoload :Merge, 'algorithmable/sort/merge'
|
4
9
|
autoload :Bubble, 'algorithmable/sort/bubble'
|
5
10
|
autoload :BinaryHeap, 'algorithmable/sort/binary_heap'
|
11
|
+
autoload :QuickSort, 'algorithmable/sort/quick_sort'
|
12
|
+
|
13
|
+
private_constant :Merge, :Bubble, :BinaryHeap, :Insertion, :QuickSort, :Selection
|
6
14
|
|
7
15
|
class << self
|
16
|
+
def quick(collection)
|
17
|
+
QuickSort.sort(collection)
|
18
|
+
end
|
19
|
+
|
8
20
|
def merge(collection)
|
9
21
|
Merge.sort(collection)
|
10
22
|
end
|
@@ -16,6 +28,22 @@ module Algorithmable
|
|
16
28
|
def binary_heap(collection)
|
17
29
|
BinaryHeap.sort(collection)
|
18
30
|
end
|
31
|
+
|
32
|
+
def selection(container)
|
33
|
+
Selection.sort(container)
|
34
|
+
end
|
35
|
+
|
36
|
+
def insertion(collection)
|
37
|
+
Insertion.sort(collection)
|
38
|
+
end
|
39
|
+
|
40
|
+
def shell(collection)
|
41
|
+
Shell.sort(collection)
|
42
|
+
end
|
43
|
+
|
44
|
+
def shuffle(collection)
|
45
|
+
Shuffle.sort(collection)
|
46
|
+
end
|
19
47
|
end
|
20
48
|
end
|
21
49
|
end
|
@@ -0,0 +1,51 @@
|
|
1
|
+
module Algorithmable
|
2
|
+
module UnionFind
|
3
|
+
def self.new(quantity)
|
4
|
+
Impl.new(quantity)
|
5
|
+
end
|
6
|
+
|
7
|
+
class Impl
|
8
|
+
attr_reader :quantity
|
9
|
+
|
10
|
+
def initialize(quantity, find_strategy = SimpleFind.new, union_strategy = SimpleUnion.new)
|
11
|
+
@index = (0..quantity).to_a
|
12
|
+
@quantity = quantity
|
13
|
+
@find_strategy = find_strategy
|
14
|
+
@union_strategy = union_strategy
|
15
|
+
end
|
16
|
+
|
17
|
+
def find(p)
|
18
|
+
@find_strategy.find(p, @index)
|
19
|
+
end
|
20
|
+
|
21
|
+
def union(p1, p2)
|
22
|
+
@union_strategy.union(p1, p2, @index)
|
23
|
+
@quantity -= 1
|
24
|
+
end
|
25
|
+
|
26
|
+
def connected?(p1, p2)
|
27
|
+
find(p1) == find(p2)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
class SimpleFind
|
32
|
+
def find(p, collection)
|
33
|
+
collection[p]
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
class SimpleUnion
|
38
|
+
def union(p1, p2, collection)
|
39
|
+
p1_id = collection[p1]
|
40
|
+
p2_id = collection[p2]
|
41
|
+
return collection if p1_id == p2_id
|
42
|
+
collection.each_index do |i|
|
43
|
+
collection[i] = p2_id if collection[i] == p1_id
|
44
|
+
end
|
45
|
+
collection
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
private_constant :Impl, :SimpleFind, :SimpleUnion
|
50
|
+
end
|
51
|
+
end
|
data/lib/algorithmable.rb
CHANGED
@@ -13,6 +13,8 @@ module Algorithmable
|
|
13
13
|
autoload :Puzzles, 'algorithmable/puzzles'
|
14
14
|
autoload :LevenshteinDistance, 'algorithmable/levenshtein_distance'
|
15
15
|
autoload :Cups, 'algorithmable/cups'
|
16
|
+
autoload :Cache, 'algorithmable/cache'
|
17
|
+
autoload :UnionFind, 'algorithmable/union_find'
|
16
18
|
|
17
19
|
class << self
|
18
20
|
def logger
|
@@ -0,0 +1,37 @@
|
|
1
|
+
#! /usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'bundler/setup'
|
4
|
+
require 'algorithmable'
|
5
|
+
require 'rbench'
|
6
|
+
|
7
|
+
job = lambda do |*_args|
|
8
|
+
sorter = Algorithmable::Sort
|
9
|
+
n = 1000
|
10
|
+
column_names = %w(selection insertion shell bubble merge quick binary_heap ruby)
|
11
|
+
|
12
|
+
f = -> (name) { public_send :column, name.to_sym }
|
13
|
+
column_names.each(&f)
|
14
|
+
|
15
|
+
g = lambda do |scope, ary|
|
16
|
+
scope.selection { sorter.selection(ary.dup) }
|
17
|
+
scope.insertion { sorter.insertion(ary.dup) }
|
18
|
+
scope.shell { sorter.shell(ary.dup) }
|
19
|
+
scope.bubble { sorter.bubble(ary.dup) }
|
20
|
+
scope.merge { sorter.merge(ary.dup) }
|
21
|
+
scope.quick { sorter.quick(ary.dup) }
|
22
|
+
scope.binary_heap { sorter.binary_heap(ary.dup) }
|
23
|
+
scope.ruby { ary.dup.sort }
|
24
|
+
end
|
25
|
+
|
26
|
+
report :presorted do
|
27
|
+
sorted_array = (0..n).to_a
|
28
|
+
g.call(self, sorted_array)
|
29
|
+
end
|
30
|
+
|
31
|
+
report :shuffled do
|
32
|
+
random_array = (0..n).to_a.shuffle
|
33
|
+
g.call(self, random_array)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
RBench.run(5, &job)
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: algorithmable
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.14.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Roman Lishtaba
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-
|
11
|
+
date: 2016-05-24 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -122,6 +122,20 @@ dependencies:
|
|
122
122
|
- - "~>"
|
123
123
|
- !ruby/object:Gem::Version
|
124
124
|
version: '0.8'
|
125
|
+
- !ruby/object:Gem::Dependency
|
126
|
+
name: rbench
|
127
|
+
requirement: !ruby/object:Gem::Requirement
|
128
|
+
requirements:
|
129
|
+
- - ">="
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: '0'
|
132
|
+
type: :development
|
133
|
+
prerelease: false
|
134
|
+
version_requirements: !ruby/object:Gem::Requirement
|
135
|
+
requirements:
|
136
|
+
- - ">="
|
137
|
+
- !ruby/object:Gem::Version
|
138
|
+
version: '0'
|
125
139
|
description: Useful algorithms for everyday usage implemented using Ruby.
|
126
140
|
email:
|
127
141
|
- roman@lishtaba.com
|
@@ -140,8 +154,27 @@ files:
|
|
140
154
|
- algorithmable.gemspec
|
141
155
|
- cucumber.yml
|
142
156
|
- lib/algorithmable.rb
|
157
|
+
- lib/algorithmable/cache.rb
|
158
|
+
- lib/algorithmable/cache/imp.rb
|
159
|
+
- lib/algorithmable/cache/primitive_max_heap.rb
|
160
|
+
- lib/algorithmable/cache/primitive_min_heap.rb
|
143
161
|
- lib/algorithmable/cups.rb
|
162
|
+
- lib/algorithmable/cups/circular_dependencies.rb
|
163
|
+
- lib/algorithmable/cups/longest_common_subsequence.rb
|
164
|
+
- lib/algorithmable/cups/merge_two_arrays.rb
|
165
|
+
- lib/algorithmable/cups/nested_lists_problem.rb
|
166
|
+
- lib/algorithmable/cups/number_of_occurrences_in_array.rb
|
144
167
|
- lib/algorithmable/cups/primitives.rb
|
168
|
+
- lib/algorithmable/cups/root_cube_issue.rb
|
169
|
+
- lib/algorithmable/cups/stacks_and_queues.rb
|
170
|
+
- lib/algorithmable/cups/stacks_and_queues/stack_sorter.rb
|
171
|
+
- lib/algorithmable/cups/stacks_and_queues/stack_with_min.rb
|
172
|
+
- lib/algorithmable/cups/stacks_and_queues/towers_of_hanoi.rb
|
173
|
+
- lib/algorithmable/cups/stacks_and_queues/triple_stack.rb
|
174
|
+
- lib/algorithmable/cups/stacks_and_queues/two_stacks_queue.rb
|
175
|
+
- lib/algorithmable/cups/stocks.rb
|
176
|
+
- lib/algorithmable/cups/task_shedule_with_coldtime.rb
|
177
|
+
- lib/algorithmable/cups/two_sum.rb
|
145
178
|
- lib/algorithmable/data_structs.rb
|
146
179
|
- lib/algorithmable/data_structs/bag.rb
|
147
180
|
- lib/algorithmable/data_structs/deque.rb
|
@@ -156,6 +189,9 @@ files:
|
|
156
189
|
- lib/algorithmable/data_structs/ordered_symbol_table.rb
|
157
190
|
- lib/algorithmable/data_structs/queue.rb
|
158
191
|
- lib/algorithmable/data_structs/stack.rb
|
192
|
+
- lib/algorithmable/data_structs/tree.rb
|
193
|
+
- lib/algorithmable/data_structs/tree/binary.rb
|
194
|
+
- lib/algorithmable/data_structs/tree/binary_search.rb
|
159
195
|
- lib/algorithmable/errors.rb
|
160
196
|
- lib/algorithmable/graphs.rb
|
161
197
|
- lib/algorithmable/graphs/traversals.rb
|
@@ -172,8 +208,16 @@ files:
|
|
172
208
|
- lib/algorithmable/sort.rb
|
173
209
|
- lib/algorithmable/sort/binary_heap.rb
|
174
210
|
- lib/algorithmable/sort/bubble.rb
|
211
|
+
- lib/algorithmable/sort/insertion.rb
|
175
212
|
- lib/algorithmable/sort/merge.rb
|
213
|
+
- lib/algorithmable/sort/quick_sort.rb
|
214
|
+
- lib/algorithmable/sort/selection.rb
|
215
|
+
- lib/algorithmable/sort/shell.rb
|
216
|
+
- lib/algorithmable/sort/shuffle.rb
|
217
|
+
- lib/algorithmable/sort/utils.rb
|
218
|
+
- lib/algorithmable/union_find.rb
|
176
219
|
- lib/algorithmable/version.rb
|
220
|
+
- script/benchmarks/sort.rb
|
177
221
|
- script/console
|
178
222
|
homepage: ''
|
179
223
|
licenses:
|