Я просто хочу остановиться на превосходных ответах Стинслага и Дбенхура. В частности, я хотел знать, будет ли SortedSet
работать лучше. Сначала меня удивило, что тип Ruby Set
не был реализован как отсортированный набор, так как я пришел из C ++; STL по умолчанию использует упорядоченный набор, и вам обычно нужно указать unordered_set
, если вы не хотите упорядочивать.
Я также хотел знать, имел ли размер набор, как предлагалось в некоторых других ответах.
require 'set'
require 'benchmark'
f = 20 # 10_000
ar1 = (1..(10*f)).to_a # 100_000 elements
ar2 = ((5*f)..(15*f)).to_a # also 100_000 elements
set1 = ar1.to_set
set2 = ar2.to_set
sset1 = SortedSet.new(ar1)
sset2 = SortedSet.new(ar2)
n = 20000 # 10
Benchmark.bm(10) do |testcase|
testcase.report('Array'){ n.times{ ar1 & ar2 } }
testcase.report('Set'){ n.times{ set1 & set2 } }
testcase.report('SortedSet') { n.times{ sset1 & sset2 } }
testcase.report('Set2'){ n.times{ ar1.select{ |element| set2.include? element } } }
testcase.report('Set2present'){ n.times{ ar1.any?{ |element| set2.include? element } } }
testcase.report('SortedSet2'){ n.times{ ar1.select{ |element| sset2.include? element } } }
testcase.report('SortedSet2present'){ n.times{ ar1.any?{ |element| sset2.include? element } } }
end
Вот результаты для f=20; n=20000
:
$ ruby set.rb
user system total real
Array 1.950000 0.010000 1.960000 ( 1.963030)
Set 3.330000 0.040000 3.370000 ( 3.374105)
SortedSet 3.810000 0.040000 3.850000 ( 3.860340)
Set2 1.410000 0.010000 1.420000 ( 1.427221)
Set2present 0.760000 0.000000 0.760000 ( 0.759447)
SortedSet2 1.420000 0.000000 1.420000 ( 1.446559)
SortedSet2present 0.770000 0.010000 0.780000 ( 0.770939)
А вот результаты для f=10000; n=10
:
$ ruby set.rb
user system total real
Array 0.910000 0.020000 0.930000 ( 0.939325)
Set 1.270000 0.010000 1.280000 ( 1.293581)
SortedSet 1.220000 0.010000 1.230000 ( 1.229650)
Set2 0.550000 0.000000 0.550000 ( 0.552708)
Set2present 0.290000 0.010000 0.300000 ( 0.291845)
SortedSet2 0.550000 0.000000 0.550000 ( 0.561049)
SortedSet2present 0.330000 0.000000 0.330000 ( 0.339950)
Так, для больших наборов, похоже, что Set
лучше, чем SortedSet
; и для небольших наборов SortedSet
лучше, чем Set
. При использовании обозначения &
, Array
быстрее, чем любой. Похоже, SortedSet2present
работает значительно эффективнее с большими наборами, тогда как Set2present
работает более эффективно с маленькими наборами.
Принимая во внимание, что Set
реализовано с использованием Hash
, SortedSet
- это RBTree
(реализовано в C). В обоих случаях &
реализован в Ruby, а не в C.