Class: Farce::Abstract::Map Abstract
- Inherits:
-
Object
- Object
- Farce::Abstract::Map
- Includes:
- Enumerable, Internal::Inspect, Internal::MarshalSupport::Map
- Defined in:
- lib/farce/abstract/map.rb,
lib/farce/integrations/bson.rb,
lib/farce/integrations/cbor.rb,
lib/farce/integrations/psych.rb,
lib/farce/integrations/msgpack.rb,
lib/farce/integrations/shared/to_json.rb,
lib/farce/integrations/active_support/map.rb
Overview
Superclass for all maps defined by Farce.
The supported methods are generally compatible with their Hash counterparts, with the notable exception of ConcurrentMap#update.
A Hash-like collection with slightly reduced functionality to allow for better concurrency models.
Constructors accept a Hash, another map, or an object whose #each yields key/value pairs. Arrays of pairs and enumerators are supported. Initial entries are inserted in source order. Local maps retain the initial entries for reuse in each scope.
dup and clone create independent storage and coordination while sharing keys and stored values.
Value modes and key normalization are preserved without transferring values again.
Copies of shareable maps remain shareable unless explicitly cloned with freeze: false.
Local copies retain the current scope's contents. Other scopes use the original constructor configuration.
Lease maps reject copying because resources cannot safely be given independent ownership controls.
Iteration order is implementation-dependent. In particular, insertion order is not guaranteed.
Implementations can compare keys and values either by equality or by identity. Operations accepting a
timeout wait at most that many seconds to acquire the access needed for the operation. A timeout must be a
finite, non-negative number, nil waits indefinitely.
Direct Known Subclasses
BSON Integration collapse
-
#as_extended_json(**options) ⇒ Hash
Represent current entries as Extended JSON, forwarding BSON's format options.
-
#bson_type ⇒ String
Identify this value as a BSON document when embedded in a document or array.
-
#to_bson(buffer = ::BSON::ByteBuffer.new) ⇒ BSON::ByteBuffer
Serialize current entries as a BSON document.
-
#to_bson_normalized_value ⇒ BSON::Document
Return current entries with keys and nested values normalized by BSON.
CBOR Integration collapse
-
#to_cbor(*arguments) ⇒ String, ...
Serialize current entries as a CBOR map.
ActiveSupport Integration collapse
-
#as_json ⇒ Hash
Convert entries using ActiveSupport's Hash JSON conversion.
-
#assert_valid_keys(*valid_keys) ⇒ self
Validate observed keys without normalizing the allowed keys.
-
#to_msgpack(*arguments) ⇒ String, ::MessagePack::Packer
Serialize current entries as a MessagePack map.
-
#to_query ⇒ String
(also: #to_param)
Encode public entries as a query string, optionally under a namespace.
JSON Integration collapse
-
#to_json(*arguments) ⇒ String
Serialize current entries as a JSON object.
Instance Method Summary collapse
-
#[](key) ⇒ BasicObject?
abstract
Look up a key without waiting for atomic-update access.
-
#[]=(key, value) ⇒ BasicObject
abstract
Associate a value with a key without a timeout.
-
#assoc(key) ⇒ Array(BasicObject, BasicObject)?
Return a two-element array containing a key and its associated value, if the key is present, or nil if the key is absent.
-
#clear ⇒ self
abstract
Remove all entries from the map.
-
#compare_by_identity? ⇒ Boolean
abstract
Whether keys are compared by identity instead of
hashandeql?. -
#compare_keys_by_identity? ⇒ Boolean
abstract
Whether keys are compared by identity instead of
hashandeql?. -
#compare_values_by_identity? ⇒ Boolean
abstract
Whether values are compared by identity instead of equality.
-
#deconstruct_keys(keys) ⇒ Hash
Support hash patterns using the same entries and key comparison as #to_h.
-
#delete(key) ⇒ BasicObject?
abstract
Remove a key and its associated value.
-
#dig(key, *rest) ⇒ BasicObject?
Implements Ruby's dig interface.
-
#each ⇒ BasicObject
abstract
Iterate over the map's key-value pairs.
-
#each_key ⇒ BasicObject
abstract
Iterate over the keys currently stored in the map.
-
#each_pair ⇒ BasicObject
abstract
Iterate over key-value pairs in the same manner as #each.
-
#each_value ⇒ BasicObject
abstract
Iterate over the values currently stored in the map.
-
#empty? ⇒ Boolean
Returns whether the map contains no entries.
-
#fetch(key, *defaults) ⇒ BasicObject
abstract
Fetch the value associated with a key, using the same missing-key behavior as Hash#fetch.
-
#fetch_values(*keys) {|key| ... } ⇒ Array<BasicObject>
Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch.
-
#getkey(key) ⇒ BasicObject?
abstract
Return the stored key that matches a lookup key.
-
#has_key? ⇒ Boolean
(also: #member?, #include?)
Alias for #key?.
-
#key(value) ⇒ BasicObject?
Return a matching key using this map's value comparison setting, or nil.
-
#key?(key) ⇒ Boolean
abstract
Test whether a key is present, including when its associated value is nil.
-
#keys ⇒ Array<BasicObject>
abstract
Return the keys currently stored in the map.
-
#length ⇒ Integer
Return the number of entries currently in the map.
-
#rassoc(value) ⇒ Array?
Return an observed key/value pair using this map's value comparison setting, or nil.
-
#shareable_keys? ⇒ Boolean
Whether the map requires keys to be Ractor-shareable.
-
#shareable_values? ⇒ Boolean
Whether the map requires values to be Ractor-shareable.
-
#size ⇒ Integer
abstract
Return the number of entries currently in the map.
-
#store(key, value) ⇒ BasicObject
Store a value using the map's assignment operation.
-
#store_if_absent(key) { ... } ⇒ BasicObject
abstract
Read an existing value or construct and store a value for an absent key.
-
#to_a ⇒ Array<Array(BasicObject, BasicObject)>
Creates a new Array containing the map's key-value pairs as two-element arrays.
-
#to_h {|key, value| ... } ⇒ Hash
Creates a new Hash containing the map's entries.
-
#to_hash ⇒ Hash
Support implicit Hash conversion using this map's #to_h implementation.
-
#to_s ⇒ String
String representation of the map, suitable for debugging.
-
#value?(value) ⇒ Boolean
(also: #has_value?)
Return whether an observed value matches using this map's value comparison setting.
-
#values_at(*keys) ⇒ Array<BasicObject>
Fetches the values associated with multiple keys, returning nil for any missing keys.
-
#weak_keys? ⇒ Boolean
Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected.
-
#weak_values? ⇒ Boolean
Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected.
Instance Method Details
#[](key) ⇒ BasicObject?
Look up a key without waiting for atomic-update access.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#[]=(key, value) ⇒ BasicObject
Associate a value with a key without a timeout.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#as_extended_json(**options) ⇒ Hash
59 |
# File 'lib/farce/integrations/bson.rb', line 59 def as_extended_json(**) = to_h.as_extended_json(**) |
#as_json ⇒ Hash
This methods is only available if ActiveSupport has been loaded.
Convert entries using ActiveSupport's Hash JSON conversion.
14 |
# File 'lib/farce/integrations/active_support/map.rb', line 14 def as_json(...) = to_h.as_json(...) |
#assert_valid_keys(*valid_keys) ⇒ self
This methods is only available if ActiveSupport has been loaded.
Validate observed keys without normalizing the allowed keys. Concurrent changes may invalidate the result immediately.
27 28 29 30 31 32 33 34 35 |
# File 'lib/farce/integrations/active_support/map.rb', line 27 def assert_valid_keys(*valid_keys) valid_keys.flatten! each_key do |key| unless valid_keys.include?(key) raise ArgumentError, "Unknown key: #{key.inspect}. Valid keys are: #{valid_keys.map(&:inspect).join(", ")}" end end self end |
#assoc(key) ⇒ Array(BasicObject, BasicObject)?
Return a two-element array containing a key and its associated value, if the key is present, or nil if the key is absent.
171 172 173 174 |
# File 'lib/farce/abstract/map.rb', line 171 def assoc(key) value = fetch(key) { return nil } [key, value] end |
#bson_type ⇒ String
This method is only available if BSON has been loaded.
Identify this value as a BSON document when embedded in a document or array.
47 |
# File 'lib/farce/integrations/bson.rb', line 47 def bson_type = ::BSON::Hash::BSON_TYPE |
#clear ⇒ self
Remove all entries from the map.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#compare_by_identity? ⇒ Boolean
Returns Whether keys are compared by identity instead of hash and eql?.
177 |
# File 'lib/farce/abstract/map.rb', line 177 def compare_by_identity? = compare_keys_by_identity? |
#compare_keys_by_identity? ⇒ Boolean
Returns Whether keys are compared by identity instead of hash and eql?.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#compare_values_by_identity? ⇒ Boolean
Returns Whether values are compared by identity instead of equality.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#deconstruct_keys(keys) ⇒ Hash
Support hash patterns using the same entries and key comparison as #to_h. Like Hash, this returns all entries regardless of the requested keys.
271 |
# File 'lib/farce/abstract/map.rb', line 271 def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument |
#delete(key) ⇒ BasicObject?
Remove a key and its associated value.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#dig(key, *rest) ⇒ BasicObject?
Implements Ruby's dig interface.
183 184 185 186 187 |
# File 'lib/farce/abstract/map.rb', line 183 def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end |
#each {|pair| ... } ⇒ self #each ⇒ Enumerator
Iterate over the map's key-value pairs. Entry consistency and access requirements depend on the implementation. Iteration order is not guaranteed to match insertion order.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#each_key {|key| ... } ⇒ self #each_key ⇒ Enumerator
Iterate over the keys currently stored in the map. Keys are not guaranteed to be yielded in insertion order.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#each_pair ⇒ BasicObject
Iterate over key-value pairs in the same manner as #each.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#each_value {|value| ... } ⇒ self #each_value ⇒ Enumerator
Iterate over the values currently stored in the map. Values are not guaranteed to be yielded in insertion order.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#empty? ⇒ Boolean
Returns whether the map contains no entries.
191 |
# File 'lib/farce/abstract/map.rb', line 191 def empty? = size.zero? |
#fetch(key) ⇒ BasicObject #fetch(key, default) ⇒ BasicObject #fetch(key) {|key| ... } ⇒ BasicObject
Fetch the value associated with a key, using the same missing-key behavior as Hash#fetch. If both a default and a block are provided, the block takes precedence and a warning is emitted.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#fetch_values(*keys) {|key| ... } ⇒ Array<BasicObject>
Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch.
239 |
# File 'lib/farce/abstract/map.rb', line 239 def fetch_values(*keys, &) = keys.map { fetch(it, &) } |
#getkey(key) ⇒ BasicObject?
Return the stored key that matches a lookup key.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#has_key? ⇒ Boolean Also known as: member?, include?
Alias for #key?
229 |
# File 'lib/farce/abstract/map.rb', line 229 def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix |
#key(value) ⇒ BasicObject?
Return a matching key using this map's value comparison setting, or nil. The first observed match is returned. No insertion order is guaranteed.
211 212 213 214 |
# File 'lib/farce/abstract/map.rb', line 211 def key(value) pair = rassoc(value) pair&.first end |
#key?(key) ⇒ Boolean
Test whether a key is present, including when its associated value is nil.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#keys ⇒ Array<BasicObject>
Return the keys currently stored in the map. The returned keys are not guaranteed to be in insertion order.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#length ⇒ Integer
Return the number of entries currently in the map.
195 |
# File 'lib/farce/abstract/map.rb', line 195 def length = size |
#rassoc(value) ⇒ Array?
Return an observed key/value pair using this map's value comparison setting, or nil. Values are unwrapped before comparison. Concurrent changes may make the result stale.
220 221 222 223 224 225 226 |
# File 'lib/farce/abstract/map.rb', line 220 def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end |
#shareable_keys? ⇒ Boolean
Some maps may still accept non-shareable keys or values, but convert them into shareable representations.
This method will still return true for such maps.
Returns Whether the map requires keys to be Ractor-shareable.
246 |
# File 'lib/farce/abstract/map.rb', line 246 def shareable_keys? = false |
#shareable_values? ⇒ Boolean
Returns Whether the map requires values to be Ractor-shareable.
249 |
# File 'lib/farce/abstract/map.rb', line 249 def shareable_values? = false |
#size ⇒ Integer
Return the number of entries currently in the map.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#store(key, value) ⇒ BasicObject
Store a value using the map's assignment operation. Concurrent maps override this method to support timeouts.
165 |
# File 'lib/farce/abstract/map.rb', line 165 def store(key, value) = self[key] = value |
#store_if_absent(key) { ... } ⇒ BasicObject
Read an existing value or construct and store a value for an absent key. Existing nil and false values count as present when the implementation permits them. The block runs without holding a map-wide lock. Implementations document their coordination guarantees, ownership requirements, and optional timeout support. A later removal or eviction can cause another call to construct a new value.
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 |
# File 'lib/farce/abstract/map.rb', line 155 class Map include Internal::MarshalSupport::Map include Enumerable include Internal::Inspect # Store a value using the map's assignment operation. # Concurrent maps override this method to support timeouts. # @param key [BasicObject] the key to store # @param value [BasicObject] the value to store # @return [BasicObject] `value` def store(key, value) = self[key] = value # Return a two-element array containing a key and its associated value, if the key is present, # or nil if the key is absent. # @param key [BasicObject] The key to look up. # @return [Array(BasicObject, BasicObject), nil] A two-element `[key, value]` array, or nil if the key is absent. def assoc(key) value = fetch(key) { return nil } [key, value] end # (see #compare_keys_by_identity?) def compare_by_identity? = compare_keys_by_identity? # Implements Ruby's [dig interface](https://docs.ruby-lang.org/en/master/language/dig_methods_rdoc.html). # @param key [BasicObject] The key to look up. # @param rest [Array<BasicObject>] Additional keys to look up in nested maps. # @return [BasicObject, nil] The value found at the nested location, or nil if any key is absent or nil. def dig(key, *rest) value = self[key] return value if rest.empty? || value.nil? value.dig(*rest) end # Returns whether the map contains no entries. # @return [Boolean] Whether the map is empty. def empty? = size.zero? # Return the number of entries currently in the map. # @return [Integer] def length = size # Return whether an observed value matches using this map's value comparison setting. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Boolean] def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end alias has_value? value? # Return a matching key using this map's value comparison setting, or nil. # The first observed match is returned. No insertion order is guaranteed. # @param value [BasicObject] the value to find # @return [BasicObject, nil] def key(value) pair = rassoc(value) pair&.first end # Return an observed key/value pair using this map's value comparison setting, or nil. # Values are unwrapped before comparison. Concurrent changes may make the result stale. # @param value [BasicObject] the value to find # @return [Array, nil] def rassoc(value) identity = compare_values_by_identity? each_pair do |key, stored| return [key, stored] if identity ? stored.equal?(value) : stored == value end nil end # Alias for {#key?} def has_key?(...) = key?(...) # rubocop:disable Naming/PredicatePrefix alias member? has_key? alias include? has_key? # Fetches the values associated with multiple keys, using the same missing-key behavior as Hash#fetch. # @yield [key] Called for each missing key. # @yieldparam key [BasicObject] The missing key. # @yieldreturn [BasicObject] The value to return for the missing key. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values. def fetch_values(*keys, &) = keys.map { fetch(it, &) } # @note # Some maps may still accept non-shareable keys or values, but convert them into shareable representations. # This method will still return `true` for such maps. # # @return [Boolean] Whether the map requires keys to be Ractor-shareable def shareable_keys? = false # @return [Boolean] Whether the map requires values to be Ractor-shareable def shareable_values? = false # Creates a new Array containing the map's key-value pairs as two-element arrays. # @return [Array<Array(BasicObject, BasicObject)>>] A new Array of `[key, value]` arrays. def to_a = each_pair.to_a # Creates a new Hash containing the map's entries. # Preserves identity comparison for keys, including when a block transforms entries. # @yieldparam key [BasicObject] an existing key # @yieldparam value [BasicObject] its value # @yieldreturn [Array(BasicObject, BasicObject)] the key and value for the new Hash # @return [Hash] A new Hash with the original entries, or the pairs returned by the block. def to_h(&) = entries_to_hash(each_pair, &) # Support implicit Hash conversion using this map's {#to_h} implementation. # @return [Hash] A new Hash containing the map's entries. def to_hash = to_h # Support hash patterns using the same entries and key comparison as {#to_h}. # Like Hash, this returns all entries regardless of the requested keys. # @param keys [Array, nil] the optional key hint supplied by Ruby's pattern matcher # @return [Hash] A new Hash containing the map's entries. def deconstruct_keys(keys) = to_h # rubocop:disable Lint/UnusedMethodArgument # Fetches the values associated with multiple keys, returning nil for any missing keys. # @param keys [Array<BasicObject>] The keys to look up. # @return [Array<BasicObject>] An array of the associated values, with nil for any missing keys. def values_at(*keys) = keys.map { self[it] } # Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected. # @return [Boolean] Whether the map uses weak references for keys. def weak_keys? = false # Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected. # @return [Boolean] Whether the map uses weak references for values. def weak_values? = false # @return [String] String representation of the map, suitable for debugging. def to_s = inspect # @api private def inspect_with(inspector) super do yield if block_given? inspector.breakable inspector.group("{", "}") do inspector.breakable "" inspector.seplist(self, nil, :each_for_inspect) do |key, value| inspector.group { inspect_pair(inspector, key, value) } end end end end protected # Convert a public value to its stored representation. # @api private def wrap_value(value) = value # Convert a stored representation to its public value. # @api private def unwrap_value(value) = value private def entries_to_hash(entries, &) return entries.to_h(&) unless compare_keys_by_identity? hash = {}.compare_by_identity entries.each do |key, value| if block_given? pair = Array.try_convert(yield(key, value)) raise TypeError, "block must return an Array or respond to #to_ary" unless pair raise ArgumentError, "block must return a two-element pair" unless pair.size == 2 key, value = pair end hash[key] = value end hash end def convert_entries(entries) return entries if Map === entries if entries.respond_to?(:to_hash) entries = Hash.try_convert(entries) raise TypeError, "entries must be a Hash or respond to #to_hash" unless entries end return entries if entries.nil? || entries.respond_to?(:each) raise TypeError, "entries must yield key/value pairs with #each" end def each_for_inspect(&) = each(&) def inspect_pair(inspector, key, value) = inspector.hash_pair(key, value) { inspect_value(inspector, value) } def inspect_value(inspector, ...) = inspector.object(...) end |
#to_a ⇒ Array<Array(BasicObject, BasicObject)>
Creates a new Array containing the map's key-value pairs as two-element arrays.
253 |
# File 'lib/farce/abstract/map.rb', line 253 def to_a = each_pair.to_a |
#to_bson(buffer = ::BSON::ByteBuffer.new) ⇒ BSON::ByteBuffer
This method is only available if BSON has been loaded.
Serialize current entries as a BSON document. Nested value wrappers are read before encoding their BSON types and payloads.
42 |
# File 'lib/farce/integrations/bson.rb', line 42 def to_bson(buffer = ::BSON::ByteBuffer.new) = to_bson_normalized_value.to_bson(buffer) |
#to_bson_normalized_value ⇒ BSON::Document
This method is only available if BSON has been loaded.
Return current entries with keys and nested values normalized by BSON.
52 |
# File 'lib/farce/integrations/bson.rb', line 52 def to_bson_normalized_value = to_h.to_bson_normalized_value |
#to_cbor(*arguments) ⇒ String, ...
29 |
# File 'lib/farce/integrations/cbor.rb', line 29 def to_cbor(...) = to_h.to_cbor(...) |
#to_h {|key, value| ... } ⇒ Hash
Creates a new Hash containing the map's entries. Preserves identity comparison for keys, including when a block transforms entries.
261 |
# File 'lib/farce/abstract/map.rb', line 261 def to_h(&) = entries_to_hash(each_pair, &) |
#to_hash ⇒ Hash
Support implicit Hash conversion using this map's #to_h implementation.
265 |
# File 'lib/farce/abstract/map.rb', line 265 def to_hash = to_h |
#to_json(*arguments) ⇒ String
This method is only available if a supported JSON library has been loaded.
Serialize current entries as a JSON object.
22 |
# File 'lib/farce/integrations/shared/to_json.rb', line 22 def to_json(...) = to_h.to_json(...) |
#to_msgpack(*arguments) ⇒ String, ::MessagePack::Packer
This method is only available if MessagePack has been loaded.
Serialize current entries as a MessagePack map.
25 |
# File 'lib/farce/integrations/msgpack.rb', line 25 def to_msgpack(...) = to_h.to_msgpack(...) |
#to_query ⇒ String Also known as: to_param
This methods is only available if ActiveSupport has been loaded.
Encode public entries as a query string, optionally under a namespace.
19 |
# File 'lib/farce/integrations/active_support/map.rb', line 19 def to_query(...) = to_h.to_query(...) |
#to_s ⇒ String
Returns String representation of the map, suitable for debugging.
287 |
# File 'lib/farce/abstract/map.rb', line 287 def to_s = inspect |
#value?(value) ⇒ Boolean Also known as: has_value?
Return whether an observed value matches using this map's value comparison setting. Values are unwrapped before comparison. Concurrent changes may make the result stale.
201 202 203 204 |
# File 'lib/farce/abstract/map.rb', line 201 def value?(value) identity = compare_values_by_identity? each_value.any? { |stored| identity ? stored.equal?(value) : stored == value } end |
#values_at(*keys) ⇒ Array<BasicObject>
Fetches the values associated with multiple keys, returning nil for any missing keys.
276 |
# File 'lib/farce/abstract/map.rb', line 276 def values_at(*keys) = keys.map { self[it] } |
#weak_keys? ⇒ Boolean
Some maps reference their keys weakly, automatically dropping entries when a key gets garbage-collected.
280 |
# File 'lib/farce/abstract/map.rb', line 280 def weak_keys? = false |
#weak_values? ⇒ Boolean
Some maps reference their values weakly, automatically dropping entries when a value gets garbage-collected.
284 |
# File 'lib/farce/abstract/map.rb', line 284 def weak_values? = false |