boxxer 0.1.2 → 0.1.7

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 94b01e461a32482c9e82ac67c445ad8ac0ff220cd2f856e9069136d75bfd2130
4
- data.tar.gz: 2af80c2e9047c380d85eba1c93827d891b1b8dfffe3cf45974a0151e85179e6a
3
+ metadata.gz: 0b6c534e695054bffd003328b0af399f894693b552667c74d8570d4a119d5b3f
4
+ data.tar.gz: 177549404aa1dc35bf73c476fa05d5c5dfed9dc59f94fc9eee7a4bc7f44effff
5
5
  SHA512:
6
- metadata.gz: 2c4b993a078e6f58cc3b617c03eeb242f7fca5680b78c25e55d663b932b30490df3996753ea6bb29a8d8bc8b1d57c2143efa0a55a3027c8cd1979ad6354d5583
7
- data.tar.gz: dde510f48b5f93f4655bc42adfdee59fcefa8c430846128d30185dc4eb104c9838e6be7817c68589a6d6a66cb5d1c75e1c4f01a2fd6fa9ec13fc5532b2f2153a
6
+ metadata.gz: b86c3486aaf605bce7be83980f8f39233a02acdc4d69d5bd437dd627fcf9c9ea6d35430caa58a18312f257245f0f66da89a36e70c8212da20f15ec72a20c9b40
7
+ data.tar.gz: 212eb85b28c726387278ddd6c6aa841535189c6bede22e2a7caaa89a21760e5a6febefe88ce6f5647e22798cba4a07f2f099b5616783b0b2bd9864910f6913f6
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- boxxer (0.1.2)
4
+ boxxer (0.1.7)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
data/README.md CHANGED
@@ -10,15 +10,13 @@ irb
10
10
  ```
11
11
 
12
12
  ```
13
+ require 'securerandom'
13
14
  require 'boxxer'
14
- weights = []
15
- 20.times { weights << rand(0.5..1).round(3) }
15
+ contents = 20.times.with_object([]) { |_, obj| obj.push(item: SecureRandom.alphanumeric(10), weight: rand(0.5..1).round(3)) }
16
16
  containers = [{ length: 47, width: 38, height: 10, tare_weight: 0.019, net_limit: 0.481 },
17
17
  { length: 40, width: 28, height: 13, tare_weight: 0.34, net_limit: 0.66 },
18
18
  { length: 40, width: 28, height: 80, tare_weight: 0.1, net_limit: 0.7 },
19
19
  { length: 40, width: 28, height: 18, tare_weight: 0.5, net_limit: 1.5 },
20
20
  { length: 40, width: 28, height: 20, tare_weight: 0.52, net_limit: 2.48 }]
21
- arranger = Boxxer::Arranger.new(containers: containers, weights: weights)
22
- arranger.call
23
- arranger.containers
21
+ boxxer = Boxxer.call(containers: containers, contents: contents)
24
22
  ```
@@ -1,55 +1,10 @@
1
- require 'boxxer/container'
1
+ require 'boxxer/handler'
2
2
  require 'boxxer/version'
3
3
 
4
4
  module Boxxer
5
5
  class Error < StandardError; end
6
6
 
7
- class Arranger
8
- attr_reader :containers, :container_count, :total_gross_weight, :total_net_weight
9
-
10
- def initialize(containers:, weights:)
11
- @available_containers = containers.sort { |container| container[:net_limit] }.reverse
12
- @largest_container = @available_containers.last
13
- @weights = weights.sort.reverse
14
- @containers = []
15
- end
16
-
17
- def call
18
- raise Error, "Largest container net_limit is #{@largest_container[:net_limit]}, but maximum weight is #{@weights.max}" if invalid_options?
19
- until @weights.empty? do
20
- container = Container.new(matching_container)
21
- complete_container(container)
22
- @containers << container
23
- end
24
- end
25
-
26
- private
27
-
28
- def total_gross_weight
29
- @containers.sum(&:gross_weight)
30
- end
31
-
32
- def total_net_weight
33
- @containers.sum(&:net_weight)
34
- end
35
-
36
- def container_count
37
- @containers.count
38
- end
39
-
40
- def complete_container(container)
41
- loop do
42
- fittable_weight = @weights.find { |weight| container.fittable?(weight) }
43
- fittable_weight.nil? ? break : container.add_weight(@weights.delete_at(@weights.index(fittable_weight)))
44
- end
45
- end
46
-
47
- def invalid_options?
48
- @weights.max > @largest_container[:net_limit]
49
- end
50
-
51
- def matching_container
52
- @available_containers.find { |container| container[:net_limit] >= @weights.sum } || @largest_container
53
- end
7
+ def self.call(options = {})
8
+ Handler.new(options).call
54
9
  end
55
10
  end
@@ -1,7 +1,7 @@
1
1
  module Boxxer
2
2
  class Container
3
- attr_reader :tare_weight, :net_weight, :gross_weight, :width, :height, :length
4
- attr_writer :weights
3
+ attr_reader :tare_weight, :width, :height, :length
4
+ attr_accessor :contents
5
5
 
6
6
  def initialize(width:, height:, length:, tare_weight:, net_limit:)
7
7
  @width = width
@@ -9,11 +9,11 @@ module Boxxer
9
9
  @length = length
10
10
  @net_limit = net_limit
11
11
  @tare_weight = tare_weight
12
- @weights = []
12
+ @contents = []
13
13
  end
14
14
 
15
15
  def net_weight
16
- (@weights.sum).truncate(3)
16
+ @contents.sum { |content| content[:weight] }.truncate(3)
17
17
  end
18
18
 
19
19
  def gross_weight
@@ -24,8 +24,8 @@ module Boxxer
24
24
  @net_limit >= net_weight + weight
25
25
  end
26
26
 
27
- def add_weight(weight)
28
- @weights.push(weight)
27
+ def add_content(content)
28
+ @contents.push(content)
29
29
  end
30
30
  end
31
31
  end
@@ -0,0 +1,58 @@
1
+ require 'boxxer/container'
2
+
3
+ module Boxxer
4
+ class Handler
5
+ attr_reader :containers
6
+
7
+ def initialize(containers:, contents:)
8
+ @available_containers = containers.sort_by { |container| container[:net_limit] }
9
+ @largest_container = @available_containers.last
10
+ @contents = contents.sort_by { |content| content[:weight] }.reverse
11
+ @containers = []
12
+ end
13
+
14
+ def call
15
+ raise Error, "Largest container net_limit is #{@largest_container[:net_limit]}, but maximum weight is #{content_max_weight}" if invalid_options?
16
+
17
+ until @contents.empty? do
18
+ container = Container.new(matching_container)
19
+ complete_container(container)
20
+ @containers << container
21
+ end
22
+ self
23
+ end
24
+
25
+ def total_gross_weight
26
+ @containers.sum(&:gross_weight).truncate(3)
27
+ end
28
+
29
+ def total_net_weight
30
+ @containers.sum(&:net_weight).truncate(3)
31
+ end
32
+
33
+ def container_count
34
+ @containers.count
35
+ end
36
+
37
+ private
38
+
39
+ def complete_container(container)
40
+ loop do
41
+ fittable_conteiner = @contents.find { |content| container.fittable?(content[:weight]) }
42
+ fittable_conteiner.nil? ? break : container.add_content(@contents.delete_at(@contents.index(fittable_conteiner)))
43
+ end
44
+ end
45
+
46
+ def content_max_weight
47
+ @contents.max { |c| c[:weight] }
48
+ end
49
+
50
+ def invalid_options?
51
+ content_max_weight[:weight] > @largest_container[:net_limit]
52
+ end
53
+
54
+ def matching_container
55
+ @available_containers.find { |container| container[:net_limit] >= @contents.sum { |content| content[:weight] } } || @largest_container
56
+ end
57
+ end
58
+ end
@@ -1,3 +1,3 @@
1
1
  module Boxxer
2
- VERSION = '0.1.2'
2
+ VERSION = '0.1.7'
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: boxxer
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.2
4
+ version: 0.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dmitry Sivoglaz
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-06-07 00:00:00.000000000 Z
11
+ date: 2020-07-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: awesome_print
@@ -101,6 +101,7 @@ files:
101
101
  - boxxer.gemspec
102
102
  - lib/boxxer.rb
103
103
  - lib/boxxer/container.rb
104
+ - lib/boxxer/handler.rb
104
105
  - lib/boxxer/version.rb
105
106
  homepage:
106
107
  licenses:
@@ -121,7 +122,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
121
122
  - !ruby/object:Gem::Version
122
123
  version: '0'
123
124
  requirements: []
124
- rubygems_version: 3.0.6
125
+ rubygems_version: 3.0.8
125
126
  signing_key:
126
127
  specification_version: 4
127
128
  summary: Picking containers, boxes, cartons, packages based on items weight