lib/haversack/sack.rb in haversack-0.3.0 vs lib/haversack/sack.rb in haversack-1.0.0
- old
+ new
@@ -1,79 +1,61 @@
-class Sack
- include Enumerable
+require 'haversack/itemcollection'
- attr_reader :capacity, :weight, :available_capacity, :current_weight, :contents
+class Sack < Haversack::ItemCollection
- def initialize(capacity:, weight:, contents: nil)
- @capacity = capacity
- @weight = weight
- self.contents = contents || [] ## Use the setter to enforce weight/capacity restrictions
- @current_weight = self.current_weight
- @available_capacity = self.available_capacity
- end
-
- def method_missing(method_id)
- Enumerable.respond_to? method_id ? @contents.send(method_id) : raise(NoMethodError)
- end
+ attr_accessor :capacity
+ attr_accessor :max_weight
- def contents=(new_contents)
- raise Haversack::KnapsackContentError if has_non_items? new_contents
- raise Haversack::KnapsackCapacityExceededError if exceeds_capacity? new_contents
- raise Haversack::KnapsackWeightExceededError if exceeds_weight? new_contents
+ def initialize(data, capacity:, max_weight:, &block)
- @contents = new_contents
- end
+ @capacity = capacity
+ @max_weight = max_weight
+
+ block_given? ? super(data, &block) : super(data)
+
+ raise Haversack::KnapsackCapacityExceededError if contents_exceed_capacity?
+ raise Haversack::KnapsackWeightExceededError if contents_exceed_weight?
+ end
- def has_non_items?(contents) ## TODO: Consider refactor: Static method? Doesn't rely on instance data.
- contents.any? { |e| !e.is_a? Haversack::Item }
+ def available_weight
+ empty? ? @max_weight : (@max_weight - weight)
end
- def current_weight
- @contents.empty? ? 0 : @contents.map { |item| item.weight }.sum
- end
-
- ## TODO: the *fit* methods duplicate behavior. Consolidate them in a future itteration.
-
- def fits_item_weight?(item)
- item.weight + @current_weight <= @weight
- end
-
def available_capacity
- @contents.empty? ? @capacity : (@capacity - @contents.length)
+ empty? ? @capacity : (@capacity - size)
end
- def fits_item_capacity?(item)
- item.size < @available_capacity
+ def fits_weight?(item)
+ item.weight <= available_weight
end
- def fits_item?(item)
- (item.is_a? Haversack::Item) && (fits_item_capacity?(item) && fits_item_weight?(item))
+ def exceeds_weight?(item)
+ !fits_weight?(item)
end
-
- def push(item) ## TODO: Return an error that describes which constraint failed
- fits_item? item ? @contents.push(item) : raise(Haversack::KnapsackContentError)
- @contents
+
+ def fits_capacity?(item)
+ item.size <= available_capacity
end
- def fits_contents?(contents)
- fits_weight?(contents) && fits_capacity?(contents)
+ def exceeds_capacity?(item)
+ !fits_capacity?(item)
end
-
- def fits_weight?(contents)
- new_weight = contents.map { |item| item.weight }.sum
- new_weight <= @weight
+
+ def fits_item?(item)
+ item.is_a?(Haversack::Item) && fits_capacity?(item) && fits_weight?(item)
end
-
- def exceeds_weight?(contents)
- !fits_weight? contents
+ alias :fits? :fits_item?
+
+ def push(item) ## TODO: Describe which constraint failed
+ fits_item?(item) ? super : raise(Haversack::KnapsackContentError)
end
-
- def fits_capacity?(contents)
- new_capacity = contents.map { |item| item.size }.sum
- new_capacity <= @capacity
+
+ private
+ def contents_exceed_weight?
+ weight > @max_weight
end
-
- def exceeds_capacity?(contents)
- !fits_capacity? contents
+
+ def contents_exceed_capacity?
+ size > @capacity
end
-
+
end