3232module Tree
3333 module Utils
3434 # Provides traversal helpers for TreeNode.
35+ # rubocop:disable Metrics/ModuleLength
3536 module TreeTraversalHandler
37+ require 'stringio'
3638 # Traverses each node (including this node) of the (sub)tree rooted at this
3739 # node by yielding the nodes to the specified block.
3840 def each # :yields: node
@@ -133,10 +135,29 @@ def each_level
133135 end
134136
135137 # Pretty prints the (sub)tree rooted at this node.
138+ # Output defaults to +$stdout+ unless an +io:+ is provided.
136139 def print_tree ( level = node_depth , max_depth = nil ,
137- block = lambda { |node , prefix |
138- puts "#{ prefix } #{ node . name } "
139- } )
140+ block = nil , io : $stdout, &custom_block )
141+ block = resolve_print_block ( block , custom_block , io )
142+ block . call ( self , tree_prefix ( level ) )
143+
144+ # Exit if the max level is defined, and reached.
145+ return unless max_depth . nil? || level < max_depth
146+
147+ # Child might be 'nil'
148+ children do |child |
149+ child &.print_tree ( level + 1 , max_depth , block , io : io )
150+ end
151+ end
152+
153+ # Returns the pretty-printed tree output as a string.
154+ def print_tree_to_s ( level = node_depth , max_depth = nil )
155+ buffer = StringIO . new
156+ print_tree ( level , max_depth , io : buffer )
157+ buffer . string
158+ end
159+
160+ def tree_prefix ( level )
140161 prefix = '' . dup # dup must be invoked to make this mutable.
141162
142163 if root?
@@ -149,16 +170,19 @@ def print_tree(level = node_depth, max_depth = nil,
149170 prefix << ( children? ? '+' : '>' )
150171 end
151172
152- block . call ( self , prefix )
173+ prefix
174+ end
153175
154- # Exit if the max level is defined, and reached.
155- return unless max_depth . nil? || level < max_depth
176+ def resolve_print_block ( block , custom_block , io )
177+ return block if block
178+ return custom_block if custom_block
156179
157- # Child might be 'nil'
158- children do |child |
159- child &.print_tree ( level + 1 , max_depth , block )
160- end
180+ lambda { |node , prefix |
181+ io . puts "#{ prefix } #{ node . name } "
182+ }
161183 end
184+ private :tree_prefix , :resolve_print_block
162185 end
186+ # rubocop:enable Metrics/ModuleLength
163187 end
164188end
0 commit comments