Class: RBTree::AutoShrinkNodePool

Inherits:
NodePool
  • Object
show all
Defined in:
lib/rbtree.rb

Overview

Internal node pool for RBTree.

Manages recycling of Node objects to reduce object allocation overhead. Includes an auto-shrink mechanism to release memory back to GC when the pool size exceeds the fluctuation range of recent active node count.

This class can be used to customize the node allocation strategy by passing an instance to #initialize.

Since:

  • 0.1.0

Instance Method Summary collapse

Constructor Details

#initialize(max_maintenance_interval: 1000, target_check_interval: 1.0, history_size: 120, buffer_factor: 1.25, reserve_ratio: 0.1) ⇒ AutoShrinkNodePool

Initializes a new AutoShrinkNodePool.

Parameters:

  • max_maintenance_interval (Integer) (defaults to: 1000)

    maximum interval between maintenance checks (default: 1000)

  • target_check_interval (Float) (defaults to: 1.0)

    target interval in seconds for maintenance checks (default: 1.0)

  • history_size (Integer) (defaults to: 120)

    duration in seconds to keep history for fluctuation analysis (default: 120)

  • buffer_factor (Float) (defaults to: 1.25)

    buffer factor to apply to observed fluctuation (default: 1.25)

  • reserve_ratio (Float) (defaults to: 0.1)

    minimum reserve capacity as a ratio of max active nodes (default: 0.1)

Since:

  • 0.1.0



2404
2405
2406
2407
2408
2409
2410
2411
2412
2413
2414
2415
2416
2417
2418
2419
2420
2421
2422
2423
2424
2425
2426
2427
2428
2429
2430
2431
# File 'lib/rbtree.rb', line 2404

def initialize(
    max_maintenance_interval: 1000,
    target_check_interval: 1.0,
    history_size: 120,
    buffer_factor: 1.25,
    reserve_ratio: 0.1)
  @pool = []
  
  @max_maintenance_interval = max_maintenance_interval
  @target_check_interval = target_check_interval
  @history_limit = history_size
  @buffer_ratio = buffer_factor
  @reserve_ratio = reserve_ratio
  
  @maintenance_count = 0
  @check_interval = 1000
  @check_count = 0
  @avg_release_rate = nil
  @last_check_time = Process.clock_gettime(Process::CLOCK_MONOTONIC)
  
  @active_nodes = 0
  @global_max_active = 0
  @global_min_active = 0
  @max_active_in_interval = 0
  @min_active_in_interval = 0
  @history = []
  @current_target_capacity = Float::INFINITY
end

Instance Method Details

#allocate(key, value, color, left, right, parent) ⇒ Object

Allocates a new node or recycles one from the pool.

Parameters:

  • key (Object)

    the key

  • value (Object)

    the value

  • color (Boolean)

    the color (true=red, false=black)

  • left (Node)

    the left child

  • right (Node)

    the right child

  • parent (Node)

    the parent node

Since:

  • 0.1.0



2441
2442
2443
2444
2445
# File 'lib/rbtree.rb', line 2441

def allocate(key, value, color, left, right, parent)
  @active_nodes += 1
  @max_active_in_interval = @active_nodes if @active_nodes > @max_active_in_interval
  super
end

#discard(count) ⇒ void

This method returns an undefined value.

Accounts for nodes dropped in bulk, so that the live-node count comes back down after a clear instead of inflating the observed fluctuation range.

Parameters:

  • count (Integer)

    the number of nodes discarded

Since:

  • 0.1.0



2468
2469
2470
2471
# File 'lib/rbtree.rb', line 2468

def discard(count)
  @active_nodes -= count
  @min_active_in_interval = @active_nodes if @active_nodes < @min_active_in_interval
end

#release(node) ⇒ Object

Releases a node back to the pool.

Checks auto-shrink logic to decide whether to keep the node or let it be GC'd.

Parameters:

  • node (Node)

    the node to release

Since:

  • 0.1.0



2452
2453
2454
2455
2456
2457
2458
2459
2460
2461
# File 'lib/rbtree.rb', line 2452

def release(node)
  @active_nodes -= 1
  @min_active_in_interval = @active_nodes if @active_nodes < @min_active_in_interval

  @check_count += 1

  perform_maintenance if @check_count >= @check_interval

  super if @pool.size < @current_target_capacity
end