contrek 1.1.7 → 1.1.9

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.
Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +13 -1
  3. data/Gemfile.lock +1 -1
  4. data/README.md +50 -23
  5. data/ext/cpp_polygon_finder/PolygonFinder/CMakeLists.txt +19 -11
  6. data/ext/cpp_polygon_finder/PolygonFinder/clean.sh +28 -0
  7. data/ext/cpp_polygon_finder/PolygonFinder/examples/example.cpp +4 -2
  8. data/ext/cpp_polygon_finder/PolygonFinder/src/Tests.cpp +1 -1
  9. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/Node.h +2 -0
  10. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/NodeCluster.cpp +66 -61
  11. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/Primitives.h +14 -0
  12. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ClippedPolygonFinder.h +1 -1
  13. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Cluster.cpp +86 -23
  14. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Cluster.h +3 -0
  15. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Cursor.cpp +24 -57
  16. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Cursor.h +7 -13
  17. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Finder.cpp +12 -9
  18. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Finder.h +2 -1
  19. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/InnerPolyline.cpp +55 -0
  20. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/InnerPolyline.h +32 -0
  21. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Merger.cpp +1 -1
  22. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Part.cpp +38 -23
  23. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Part.h +1 -2
  24. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Polyline.cpp +21 -0
  25. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Polyline.h +4 -0
  26. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Queueable.h +1 -0
  27. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Sequence.cpp +14 -0
  28. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Sequence.h +14 -0
  29. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Shape.cpp +15 -6
  30. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Shape.h +11 -3
  31. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ShapePool.cpp +42 -0
  32. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ShapePool.h +34 -0
  33. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Tile.cpp +72 -11
  34. data/ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Tile.h +9 -1
  35. data/ext/cpp_polygon_finder/cpp_polygon_finder.cpp +4 -0
  36. data/lib/contrek/finder/concurrent/cluster.rb +58 -9
  37. data/lib/contrek/finder/concurrent/cursor.rb +11 -19
  38. data/lib/contrek/finder/concurrent/finder.rb +8 -2
  39. data/lib/contrek/finder/concurrent/inner_polyline.rb +49 -0
  40. data/lib/contrek/finder/concurrent/part.rb +26 -12
  41. data/lib/contrek/finder/concurrent/polyline.rb +46 -0
  42. data/lib/contrek/finder/concurrent/queueable.rb +0 -17
  43. data/lib/contrek/finder/concurrent/sequence.rb +21 -0
  44. data/lib/contrek/finder/concurrent/shape.rb +29 -2
  45. data/lib/contrek/finder/concurrent/tile.rb +36 -7
  46. data/lib/contrek/finder/node.rb +3 -1
  47. data/lib/contrek/finder/node_cluster.rb +56 -48
  48. data/lib/contrek/version.rb +1 -1
  49. data/lib/contrek.rb +1 -0
  50. metadata +9 -2
@@ -1,8 +1,13 @@
1
1
  module Contrek
2
2
  module Concurrent
3
3
  class Sequence
4
+ attr_accessor :vertical_bounds, :shape
4
5
  prepend Queueable
5
6
 
7
+ def initialize
8
+ @vertical_bounds = nil
9
+ end
10
+
6
11
  def is_not_vertical
7
12
  return false if size < 2
8
13
  x0 = head.payload[:x]
@@ -13,6 +18,22 @@ module Contrek
13
18
  end
14
19
  false
15
20
  end
21
+
22
+ def compute_vertical_bounds!
23
+ return if size == 0
24
+ min_y = Float::INFINITY
25
+ max_y = 0
26
+ get_vector_cache.each do |pos|
27
+ y = pos[:y]
28
+ min_y = y if y < min_y
29
+ max_y = y if y > max_y
30
+ end
31
+ @vertical_bounds = {min: min_y, max: max_y}
32
+ end
33
+
34
+ def get_vector_cache
35
+ @vector_cache ||= to_a
36
+ end
16
37
  end
17
38
  end
18
39
  end
@@ -1,10 +1,37 @@
1
1
  module Contrek
2
2
  module Concurrent
3
3
  class Shape
4
- attr_accessor :outer_polyline, :inner_polylines
4
+ attr_accessor :outer_polyline, :inner_polylines, :merged_to_shape, :parent_inner_polyline,
5
+ :reassociation_skip
6
+ attr_reader :parent_shape, :children_shapes
7
+
8
+ def initialize
9
+ @parent_shape = nil
10
+ @merged_to_shape = nil
11
+ @parent_inner_polyline = nil
12
+ @children_shapes = []
13
+ @reassociation_skip = false
14
+ end
15
+
16
+ def self.init_by(set_outer_polyline, set_inner_polylines)
17
+ s = Shape.new
18
+ s.outer_polyline = set_outer_polyline
19
+ s.inner_polylines = set_inner_polylines
20
+ s
21
+ end
5
22
 
6
23
  def clear_inner!
7
- @inner_polylines = []
24
+ @inner_polylines.clear
25
+ end
26
+
27
+ def set_parent_shape(shape)
28
+ @parent_shape&.children_shapes&.delete(self)
29
+ @parent_shape = shape
30
+ shape.children_shapes << self if shape
31
+ end
32
+
33
+ def info
34
+ "Shape (outer_polyline = #{outer_polyline.named}, children count = #{@children_shapes.size}"
8
35
  end
9
36
  end
10
37
  end
@@ -28,7 +28,7 @@ module Contrek
28
28
 
29
29
  def initial_process!(finder)
30
30
  result = finder.process_info
31
- assign_raw_polygons!(result[:polygons])
31
+ assign_raw_polygons!(result[:polygons], result.metadata[:treemap])
32
32
  end
33
33
 
34
34
  def boundary_shapes
@@ -49,7 +49,9 @@ module Contrek
49
49
  end
50
50
 
51
51
  def assign_shapes!(shapes)
52
- shapes.each { |s| s.outer_polyline.tile = self }
52
+ shapes.each do |s|
53
+ s.outer_polyline.tile = self
54
+ end
53
55
  @shapes = shapes
54
56
  end
55
57
 
@@ -57,7 +59,23 @@ module Contrek
57
59
  @shapes.filter_map do |shape|
58
60
  unless shape.outer_polyline.empty?
59
61
  {outer: shape.outer_polyline.raw,
60
- inner: shape.inner_polylines}
62
+ inner: shape.inner_polylines.map(&:raw)}
63
+ end
64
+ end
65
+ end
66
+
67
+ def compute_treemap
68
+ @shapes_map = {}
69
+ shape_index = 0
70
+
71
+ @shapes.map do |shape|
72
+ next if shape.outer_polyline.empty?
73
+ @shapes_map[shape] = shape_index
74
+ shape_index += 1
75
+ if shape.parent_shape
76
+ [@shapes_map[shape.parent_shape], shape.parent_shape.inner_polylines.index(shape.parent_inner_polyline)]
77
+ else
78
+ [-1, -1]
61
79
  end
62
80
  end
63
81
  end
@@ -74,13 +92,24 @@ module Contrek
74
92
  "#{self.class}[#{@name}]"
75
93
  end
76
94
 
77
- def assign_raw_polygons!(raw_polylines)
95
+ def assign_raw_polygons!(raw_polylines, treemap = nil)
78
96
  @shapes = []
79
- raw_polylines.each do |raw_polyline|
97
+ shapes_map = {}
98
+ raw_polylines.each_with_index do |raw_polyline, polyline_index|
80
99
  next if raw_polyline[:bounds][:max_x] - raw_polyline[:bounds][:min_x] == 0
81
- @shapes << Shape.new.tap do |shape|
100
+ shape = Shape.new.tap do |shape|
82
101
  shape.outer_polyline = Polyline.new(tile: self, polygon: raw_polyline[:outer], shape: shape, bounds: raw_polyline[:bounds])
83
- shape.inner_polylines = raw_polyline[:inner]
102
+ shape.inner_polylines = raw_polyline[:inner].map { |raw| InnerPolyline.new(shape: shape, raw_coordinates: raw) }
103
+ end
104
+ @shapes << shape
105
+
106
+ if treemap && (treemap_entry = treemap[polyline_index])
107
+ shapes_map[polyline_index] = shape
108
+ if treemap_entry != [-1, -1]
109
+ parent = shapes_map[treemap_entry.first]
110
+ shape.set_parent_shape(parent)
111
+ shape.parent_inner_polyline = parent.inner_polylines[treemap_entry.last]
112
+ end
84
113
  end
85
114
  end
86
115
  end
@@ -5,7 +5,7 @@ module Contrek
5
5
 
6
6
  attr_reader :min_x, :max_x, :y, :name, :tangs_sequence, :tangs_count, :data_pointer,
7
7
  :upper_start, :upper_end, :lower_start, :lower_end, :start_point, :end_point
8
- attr_accessor :track, :abs_x_index, :outer_index, :inner_index
8
+ attr_accessor :track, :abs_x_index, :outer_index, :inner_index, :inner_left_index, :inner_right_index
9
9
 
10
10
  T_UP = -1
11
11
  T_DOWN = 1
@@ -39,6 +39,8 @@ module Contrek
39
39
  @down_indexer = 0
40
40
  @outer_index = -1
41
41
  @inner_index = -1
42
+ @inner_left_index = -1
43
+ @inner_right_index = -1
42
44
  @upper_start = Float::INFINITY
43
45
  @upper_end = -1
44
46
  @lower_start = Float::INFINITY
@@ -6,7 +6,7 @@ module Contrek
6
6
 
7
7
  def initialize(h, options)
8
8
  @options = options
9
- @vert_nodes = Array.new(h) { [] } # per y immetto i nodi
9
+ @vert_nodes = Array.new(h) { [] }
10
10
  @sequences = []
11
11
  @polygons = []
12
12
  @treemap = []
@@ -76,57 +76,60 @@ module Contrek
76
76
  plot_node(next_node, root_node, bounds, versus, @options[:strict_bounds]) if @nodes > 0 && !next_node.nil?
77
77
 
78
78
  draw_sequence(bitmap, "X") unless bitmap.nil?
79
- @polygons << {outer: @sequence_coords, inner: [], bounds: (bounds.to_h if @options[:bounds])}.compact if @sequence_coords.size >= 2
80
- @sequences << @plot_sequence
81
-
82
- @count = 0
83
- index_inner = 0
84
- while @inner_plot.size > 0
85
- @plot_sequence = []
86
- @sequence_coords = []
87
- # mia test
88
- first = @inner_plot.find { |x| x.tangs_count <= 2 } || @inner_plot.first
89
-
90
- @plot_sequence << first
91
- @inner_plot.delete(first)
92
- @root_nodes.delete(first)
93
-
94
- first.inner_index = index_inner
95
-
96
- # @count += 1
97
- # if @count > 10000
98
- # puts "Houston, we have a problem!"
99
- # break
100
- # end
101
-
102
- next_node = if (first.track & Contrek::Finder::Node::OMAX) != 0
103
- if inner_v == :a
104
- vert_nodes[first.y + Node::T_UP][first.upper_start]
79
+
80
+ if @sequence_coords.size >= 2
81
+ @polygons << {outer: @sequence_coords, inner: [], bounds: (bounds.to_h if @options[:bounds])}.compact
82
+ @sequences << @plot_sequence
83
+
84
+ @count = 0
85
+ index_inner = 0
86
+ while @inner_plot.size > 0
87
+ @plot_sequence = []
88
+ @sequence_coords = []
89
+ # mia test
90
+ first = @inner_plot.find { |x| x.tangs_count <= 2 } || @inner_plot.first
91
+
92
+ @plot_sequence << first
93
+ @inner_plot.delete(first)
94
+ @root_nodes.delete(first)
95
+
96
+ first.inner_index = index_inner
97
+
98
+ # @count += 1
99
+ # if @count > 10000
100
+ # puts "Houston, we have a problem!"
101
+ # break
102
+ # end
103
+
104
+ next_node = if (first.track & Contrek::Finder::Node::OMAX) != 0
105
+ if inner_v == :a
106
+ vert_nodes[first.y + Node::T_UP][first.upper_start]
107
+ else
108
+ vert_nodes[first.y + Node::T_DOWN][first.lower_start]
109
+ end
110
+ elsif inner_v == :a
111
+ vert_nodes[first.y + Node::T_DOWN][first.lower_end]
105
112
  else
106
- vert_nodes[first.y + Node::T_DOWN][first.lower_start]
113
+ vert_nodes[first.y + Node::T_UP][first.upper_end]
107
114
  end
108
- elsif inner_v == :a
109
- vert_nodes[first.y + Node::T_DOWN][first.lower_end]
110
- else
111
- vert_nodes[first.y + Node::T_UP][first.upper_end]
112
- end
113
115
 
114
- if !next_node.nil?
115
- @sequence_coords << next_node.coords_entering_to(first, inner_v, Contrek::Finder::Node::INNER)
116
- end
116
+ if !next_node.nil?
117
+ @sequence_coords << next_node.coords_entering_to(first, inner_v, Contrek::Finder::Node::INNER)
118
+ end
117
119
 
118
- plot_inner_node(next_node, inner_v, first, root_node, options[:strict_bounds]) if !next_node.nil?
120
+ plot_inner_node(next_node, inner_v, first, root_node, options[:strict_bounds]) if !next_node.nil?
119
121
 
120
- draw_sequence(bitmap, "+") unless bitmap.nil?
122
+ draw_sequence(bitmap, "+") unless bitmap.nil?
121
123
 
122
- @polygons.last[:inner] << @sequence_coords
124
+ @polygons.last[:inner] << @sequence_coords
123
125
 
124
- @inner_plot.grab(@inner_new)
125
- index_inner += 1
126
+ @inner_plot.grab(@inner_new)
127
+ index_inner += 1
128
+ end
129
+ # tree
130
+ @treemap << ((versus == :a) ? test_in_hole_a(root_node) : test_in_hole_o(root_node)) if @options.has_key?(:treemap)
131
+ index_order += 1
126
132
  end
127
- # tree
128
- @treemap << ((versus == :a) ? test_in_hole_a(root_node) : test_in_hole_o(root_node)) if @options.has_key?(:treemap)
129
- index_order += 1
130
133
  end
131
134
  end
132
135
 
@@ -141,7 +144,7 @@ module Contrek
141
144
  tnext = @vert_nodes[node.y][start_right]
142
145
  if tnext.outer_index == cindex
143
146
  if (tnext.track & Contrek::Finder::Node::IMIN) != 0
144
- return [cindex, prev.inner_index]
147
+ return [cindex, (prev.inner_right_index == -1) ? prev.inner_left_index : prev.inner_right_index]
145
148
  else
146
149
  return [-1, -1]
147
150
  end
@@ -165,7 +168,7 @@ module Contrek
165
168
  tnext = @vert_nodes[node.y][start_right]
166
169
  if tnext.outer_index == cindex
167
170
  if (tnext.track & Contrek::Finder::Node::IMAX) != 0
168
- return [cindex, prev.inner_index]
171
+ return [cindex, (prev.inner_left_index == -1) ? prev.inner_right_index : prev.inner_left_index]
169
172
  else
170
173
  return [-1, -1]
171
174
  end
@@ -191,13 +194,19 @@ module Contrek
191
194
  # coordinates in @sequence_coords
192
195
  def plot_inner_node(node, versus, stop_at, start_node, strict_bounds = false)
193
196
  node.outer_index = start_node.outer_index
194
- node.inner_index = stop_at.inner_index
195
197
  @root_nodes.delete(node)
196
198
  @inner_plot.delete(node)
197
199
  last_node = @plot_sequence.last
198
200
  next_node = node.my_next(last_node, versus, :inner)
199
201
  @plot_sequence << node
200
202
 
203
+ first_is_max = ((node.y > last_node.y) == (versus == :a))
204
+ if first_is_max
205
+ node.inner_right_index = stop_at.inner_index if node.inner_right_index == -1
206
+ elsif node.inner_left_index == -1
207
+ node.inner_left_index = stop_at.inner_index
208
+ end
209
+
201
210
  plot = true
202
211
  if next_node.y == last_node.y
203
212
  virtual_index = node.tangs_sequence.send((versus == :a) ? :first : :last)
@@ -211,7 +220,6 @@ module Contrek
211
220
  end
212
221
  end
213
222
  elsif strict_bounds
214
- first_is_max = ((node.y > last_node.y) == (versus == :a))
215
223
  @sequence_coords << {y: node.y, x: (first_is_max ? last_node.max_x : last_node.min_x)}
216
224
  @sequence_coords << {y: node.y, x: (first_is_max ? next_node.min_x : next_node.max_x)}
217
225
  end
@@ -1,3 +1,3 @@
1
1
  module Contrek
2
- VERSION = "1.1.7"
2
+ VERSION = "1.1.9"
3
3
  end
data/lib/contrek.rb CHANGED
@@ -29,6 +29,7 @@ require "contrek/finder/concurrent/position"
29
29
  require "contrek/finder/concurrent/sequence"
30
30
  require "contrek/finder/concurrent/shape"
31
31
  require "contrek/finder/concurrent/tile"
32
+ require "contrek/finder/concurrent/inner_polyline"
32
33
  require "contrek/finder/concurrent/polyline"
33
34
  require "contrek/finder/concurrent/cluster"
34
35
  require "contrek/finder/concurrent/finder"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: contrek
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.7
4
+ version: 1.1.9
5
5
  platform: ruby
6
6
  authors:
7
7
  - Emanuele Cesaroni
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-03-23 00:00:00.000000000 Z
11
+ date: 2026-04-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rspec
@@ -143,6 +143,7 @@ files:
143
143
  - contrek.png
144
144
  - ext/cpp_polygon_finder/PolygonFinder/CMakeLists.txt
145
145
  - ext/cpp_polygon_finder/PolygonFinder/LICENSE_AGPL.txt
146
+ - ext/cpp_polygon_finder/PolygonFinder/clean.sh
146
147
  - ext/cpp_polygon_finder/PolygonFinder/examples/example.cpp
147
148
  - ext/cpp_polygon_finder/PolygonFinder/images/graphs_1024x1024.png
148
149
  - ext/cpp_polygon_finder/PolygonFinder/images/labyrinth.png
@@ -176,6 +177,7 @@ files:
176
177
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/Polygon.h
177
178
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/PolygonFinder.cpp
178
179
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/PolygonFinder.h
180
+ - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/Primitives.h
179
181
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/RectBounds.h
180
182
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ClippedPolygonFinder.cpp
181
183
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ClippedPolygonFinder.h
@@ -193,6 +195,8 @@ files:
193
195
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/HorizontalMerger.h
194
196
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Hub.cpp
195
197
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Hub.h
198
+ - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/InnerPolyline.cpp
199
+ - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/InnerPolyline.h
196
200
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Merger.cpp
197
201
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Merger.h
198
202
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Part.cpp
@@ -213,6 +217,8 @@ files:
213
217
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Sequence.h
214
218
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Shape.cpp
215
219
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Shape.h
220
+ - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ShapePool.cpp
221
+ - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/ShapePool.h
216
222
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Tile.cpp
217
223
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/Tile.h
218
224
  - ext/cpp_polygon_finder/PolygonFinder/src/polygon/finder/concurrent/VerticalMerger.cpp
@@ -259,6 +265,7 @@ files:
259
265
  - lib/contrek/finder/concurrent/finder.rb
260
266
  - lib/contrek/finder/concurrent/horizontal_merger.rb
261
267
  - lib/contrek/finder/concurrent/hub.rb
268
+ - lib/contrek/finder/concurrent/inner_polyline.rb
262
269
  - lib/contrek/finder/concurrent/listable.rb
263
270
  - lib/contrek/finder/concurrent/merger.rb
264
271
  - lib/contrek/finder/concurrent/part.rb