Module: Tins::Subhash

Included in:
Hash
Defined in:
lib/tins/subhash.rb

Overview

Tins::Subhash provides methods for creating filtered subsets of hashes based on pattern matching against keys.

The subhash method allows you to extract key-value pairs from a hash that match specified patterns, making it easy to work with subsets of hash data based on naming conventions or other criteria.

Examples:

Basic usage with string patterns

hash = { 'foo' => 1, 'bar' => 2, 'foobar' => 3 }
sub = hash.subhash('foo')
# => { 'foo' => 1, 'foobar' => 3 }

Usage with regular expressions

hash = { 'foo' => 1, 'barfoot' => 2, 'foobar' => 3 }
sub = hash.subhash(/^foo/)
# => { 'foo' => 1, 'foobar' => 3 }

Usage with block for value transformation

hash = { 'foo' => 1, 'bar' => 2, 'foobar' => 3 }
sub = hash.subhash('foo') { |key, value, match_data| value * 2 }
# => { 'foo' => 2, 'foobar' => 6 }

Instance Method Summary collapse

Instance Method Details

#subhash(*patterns) {|key, value, match_data| ... } ⇒ Hash

Create a subhash from this hash containing only key-value pairs where the key matches any of the given patterns.

Patterns can be:

  • Regular expressions (matched against key strings)

  • Strings (exact string matching)

  • Symbols (converted to strings for matching)

  • Any object that implements === operator

Yields:

  • (key, value, match_data)

    Optional block to transform values

Yield Parameters:

  • key (String)

    The original hash key

  • value (Object)

    The original hash value

  • match_data (MatchData, nil)

    Match data when pattern is regex, nil otherwise



39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
# File 'lib/tins/subhash.rb', line 39

def subhash(*patterns)
  patterns.map! do |pat|
    pat = pat.to_sym.to_s if pat.respond_to?(:to_sym)
    pat.respond_to?(:match) ? pat : pat.to_s
  end
  result =
    if default_proc
      self.class.new(&default_proc)
    else
      self.class.new(default)
    end
  if block_given?
    each do |k, v|
      patterns.each { |pat|
        if pat === k.to_s
          result[k] = yield(k, v, $~)
          break
        end
      }
    end
  else
    each do |k, v|
      result[k] = v if patterns.any? { |pat| pat === k.to_s }
    end
  end
  result
end