Class: WeightedTable
- Inherits:
-
Object
- Object
- WeightedTable
- Defined in:
- lib/weighted_table.rb
Overview
This class contains objects and associate weights to them. So that you can sample the object according to their weights.
Constant Summary collapse
- BASE_WEIGHT =
0
Class Method Summary collapse
-
.from_file(filename) ⇒ Object
Read the table from a file.
-
.from_flat_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ data, data, data ] Example : [ :foo, :foo, :bar ].
-
.from_weighted_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ [ weight, data ], [ weight, data ], … ] Example : [ [ 2, :foo ], [ 1, :bar ] ].
Instance Method Summary collapse
-
#from_weighted_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ [ weight, data ], [ weight, data ], … ] Example : [ [ 2, :foo ], [ 1, :bar ] ].
-
#initialize(floating_points: false) ⇒ WeightedTable
constructor
Initialize a WeightedTable setting floating_points to true indicate that you will work with floating points rather than integers.
-
#sample ⇒ Object
Return a random item from a WeightedTable.
-
#to_file(filename) ⇒ Object
Save the table to a file.
Constructor Details
#initialize(floating_points: false) ⇒ WeightedTable
Initialize a WeightedTable setting floating_points to true indicate that you will work with floating points rather than integers.
12 13 14 15 16 |
# File 'lib/weighted_table.rb', line 12 def initialize( floating_points: false ) @weights = [] @max_weight = BASE_WEIGHT @floating_points = floating_points end |
Class Method Details
.from_file(filename) ⇒ Object
Read the table from a file
94 95 96 |
# File 'lib/weighted_table.rb', line 94 def self.from_file( filename ) YAML.load_file( filename ) end |
.from_flat_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ data, data, data ] Example : [ :foo, :foo, :bar ]
59 60 61 |
# File 'lib/weighted_table.rb', line 59 def self.from_flat_table( table ) from_weighted_table( table.group_by{ |e| e }.map{ |k, v| [ v.count, k ] } ) end |
.from_weighted_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ [ weight, data ], [ weight, data ], … ] Example : [ [ 2, :foo ], [ 1, :bar ] ]
23 24 25 |
# File 'lib/weighted_table.rb', line 23 def self.from_weighted_table( table ) WeightedTable.new.from_weighted_table( table ) end |
Instance Method Details
#from_weighted_table(table) ⇒ WeightedTable
Load a WeightedTable with data Data format must be : [ [ weight, data ], [ weight, data ], … ] Example : [ [ 2, :foo ], [ 1, :bar ] ]
32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 |
# File 'lib/weighted_table.rb', line 32 def from_weighted_table( table ) raise 'Table must contain at least one element' if table.empty? # We may call this method many time for an existing object, so we must clear it @weights.clear base = BASE_WEIGHT w = nil table.each do |weight, data| w = base + weight @weights << [base, w, data] base = w end @max_weight = w # p @weights, @max_weight self end |
#sample ⇒ Object
Return a random item from a WeightedTable
66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 |
# File 'lib/weighted_table.rb', line 66 def sample # ... means that @max_weight is excluded if @floating_points r = Kernel.rand( 0.0...@max_weight.to_f ) else r = Kernel.rand( 0...@max_weight ) end # p r @weights.each do |base_weight, max_weight, data| return data if r >= base_weight && r < max_weight end raise 'Rand not in key range' end |
#to_file(filename) ⇒ Object
Save the table to a file
86 87 88 89 90 |
# File 'lib/weighted_table.rb', line 86 def to_file( filename ) File.open( filename, 'w' ) do |f| f.write( to_yaml ) end end |