Class: ANTLR3::AST::BaseTree

Inherits:
Array
  • Object
show all
Extended by:
ClassMacros
Includes:
Tree
Defined in:
lib/antlr3/tree.rb

Overview

A base implementation of an Abstract Syntax Tree Node. It mainly defines the methods and attributes required to implement the parent-node-children relationship that characterize a tree; it does not provide any logic concerning a node's token payload.

Direct Known Subclasses

CommonTree

Instance Attribute Summary collapse

Attributes included from Tree

#child_index, #column, #line, #start_index, #stop_index, #text, #token, #type

Instance Method Summary collapse

Methods included from Tree

#ancestors, #depth, #each_ancestor, #has_child?, #root, #siblings

Methods inherited from Array

#pad, #pad!

Constructor Details

#initialize(node = nil) ⇒ BaseTree

Returns a new instance of BaseTree


317
318
319
320
321
# File 'lib/antlr3/tree.rb', line 317

def initialize( node = nil )
  super()
  @parent = nil
  @child_index = 0
end

Instance Attribute Details

#parentObject

Returns the value of attribute parent


313
314
315
# File 'lib/antlr3/tree.rb', line 313

def parent
  @parent
end

Instance Method Details

#add_child(child_tree) ⇒ Object


332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
# File 'lib/antlr3/tree.rb', line 332

def add_child( child_tree )
  child_tree.nil? and return
  if child_tree.flat_list?
    self.equal?( child_tree.children ) and
      raise ArgumentError, "attempt to add child list to itself"
    child_tree.each_with_index do | child, index |
      child.parent = self
      child.child_index = length + index
    end
    concat( child_tree )
  else
    child_tree.child_index = length
    child_tree.parent = self
    self << child_tree
  end
  return( self )
end

#childrenObject


323
# File 'lib/antlr3/tree.rb', line 323

def children() self end

#delete_child(index) ⇒ Object


367
368
369
370
# File 'lib/antlr3/tree.rb', line 367

def delete_child( index )
  killed = delete_at( index ) and freshen( index )
  return killed
end

#detachObject


350
351
352
353
354
# File 'lib/antlr3/tree.rb', line 350

def detach
  @parent = nil
  @child_index = -1
  return( self )
end

#first_with_type(tree_type) ⇒ Object


328
329
330
# File 'lib/antlr3/tree.rb', line 328

def first_with_type( tree_type )
  find { | child | child.type == tree_type }
end

#flat_list?Boolean

Returns:

  • (Boolean)

386
387
388
# File 'lib/antlr3/tree.rb', line 386

def flat_list?
  false
end

#freshen(offset = 0) ⇒ Object


390
391
392
393
394
395
396
# File 'lib/antlr3/tree.rb', line 390

def freshen( offset = 0 )
  for i in offset ... length
    node = self[ i ]
    node.child_index = i
    node.parent = self
  end
end

#inspectObject


408
409
410
411
412
413
414
415
# File 'lib/antlr3/tree.rb', line 408

def inspect
  empty? and return to_s
  buffer = ''
  buffer << '(' << to_s << ' ' unless flat_list?
  buffer << map { | c | c.inspect }.join( ' ' )
  buffer << ')' unless flat_list?
  return( buffer )
end

#pruneObject

Raises:

  • (StopIteration)

436
437
438
# File 'lib/antlr3/tree.rb', line 436

def prune
  raise StopIteration
end

#replace_children(start, stop, new_tree) ⇒ Object


372
373
374
375
376
377
378
379
380
381
382
383
384
# File 'lib/antlr3/tree.rb', line 372

def replace_children( start, stop, new_tree )
  start >= length or stop >= length and
    raise IndexError, ( "| indices span beyond the number of children:\n|  children.length = \#{ length }\n|  start = \#{ start_index.inspect }\n|  stop  = \#{ stop_index.inspect }\n" ).gsub!( /^\s+\| /,'' )
  new_children = new_tree.flat_list? ? new_tree : [ new_tree ]
  self[ start .. stop ] = new_children
  freshen( start_index )
  return self
end

#root?Boolean

protected :sanity_check, :freshen

Returns:

  • (Boolean)

443
# File 'lib/antlr3/tree.rb', line 443

def root?() @parent.nil? end

#sanity_check(parent = nil, i = -1 )) ⇒ Object


398
399
400
401
402
403
404
405
406
# File 'lib/antlr3/tree.rb', line 398

def sanity_check( parent = nil, i = -1 )
  parent == @parent or
    raise TreeInconsistency.failed_parent_check!( parent, @parent )
  i == @child_index or
    raise TreeInconsistency.failed_index_check!( i, @child_index )
  each_with_index do | child, index |
    child.sanity_check( self, index )
  end
end

#set_child(index, tree) ⇒ Object


359
360
361
362
363
364
365
# File 'lib/antlr3/tree.rb', line 359

def set_child( index, tree )
  return if tree.nil?
  tree.flat_list? and raise ArgumentError, "Can't set single child to a list"
  tree.parent = self
  tree.child_index = index
  self[ index ] = tree
end

#walkObject


417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
# File 'lib/antlr3/tree.rb', line 417

def walk
  block_given? or return( enum_for( :walk ) )
  stack = []
  cursor = self
  while true
    begin
      yield( cursor )
      stack.push( Array[ *cursor ] ) unless cursor.empty?
    rescue StopIteration
      # skips adding children to prune the node
    ensure
      break if stack.empty?
      cursor = stack.last.shift
      stack.pop if stack.last.empty?
    end
  end
  return self
end