Class: Hash
| Relationships & Source Files | |
| Super Chains via Extension / Inclusion / Inheritance | |
|
Instance Chain:
self,
::Enumerable
|
|
| Inherits: | Object |
| Defined in: | hash.c, hash.rb |
Class Method Summary
-
.[] ⇒ Hash
Returns a new Hash object populated with the given objects, if any.
-
.new(default_value = nil, capacity: 0) ⇒ Hash
constructor
Returns a new empty Hash object.
-
.ruby2_keywords_hash(hash) ⇒ Hash
Duplicates a given hash and adds a ruby2_keywords flag.
-
.ruby2_keywords_hash?(hash) ⇒ Boolean
Checks if a given hash is flagged by Module#ruby2_keywords (or Proc#ruby2_keywords).
-
.try_convert(object) ⇒ Object, ...
If
objectis a hash, returnsobject.
Instance Attribute Summary
-
#compare_by_identity ⇒ self
readonly
Sets
selfto compare keys using identity (rather than mere equality); returnsself: -
#compare_by_identity? ⇒ Boolean
readonly
Returns whether #compare_by_identity has been called:
-
#default_proc ⇒ Proc?
rw
Returns the default proc for
self(seeHashDefault): -
#default_proc=(proc) ⇒ Proc
rw
Sets the default proc for
selftoproc(seeHashDefault): -
#empty? ⇒ Boolean
readonly
Returns
trueif there are no hash entries,falseotherwise:
Instance Method Summary
-
#<(other_hash) ⇒ Boolean
Returns
trueif the entries ofselfare a proper subset of the entries ofother_hash,falseotherwise: -
#<=(other_hash) ⇒ Boolean
Returns
trueif the entries ofselfare a subset of the entries ofother_hash,falseotherwise: -
#==(object) ⇒ Boolean
Returns whether
selfandobjectare equal. -
#>(other_hash) ⇒ Boolean
Returns
trueif the entries ofselfare a proper superset of the entries ofother_hash,falseotherwise: -
#>=(other_hash) ⇒ Boolean
Returns
trueif the entries ofselfare a superset of the entries ofother_hash,falseotherwise: -
#[](key) ⇒ Object
Searches for a hash key equivalent to the given #key; see
HashKey Equivalence. -
#[]=(key, object) ⇒ Object
(also: #store)
Associates the given
objectwith the given #key; returnsobject. -
#any? ⇒ Boolean
Returns
trueif any element satisfies a given criterion;falseotherwise. -
#assoc(key) ⇒ entry?
If the given #key is found, returns its entry as a 2-element array containing that key and its value:
-
#clear ⇒ self
Removes all entries from
self; returns emptiedself. -
#compact ⇒ Hash
Returns a copy of
selfwith allnil-valued entries removed: -
#compact! ⇒ self?
If
selfcontains anynil-valued entries, returnsselfwith allnil-valued entries removed; returnsnilotherwise: -
#default ⇒ Object
Returns the default value for the given #key.
-
#default=(value) ⇒ Object
Sets the default value to
value; returnsvalue: -
#delete(key) ⇒ value?
If an entry for the given #key is found, deletes the entry and returns its associated value; otherwise returns
nilor calls the given block. -
#delete_if {|key, value| ... } ⇒ self
With a block given, calls the block with each key-value pair, deletes each entry for which the block returns a truthy value, and returns
self: -
#dig(key, *identifiers) ⇒ Object
Finds and returns an object found in nested objects, as specified by #key and
identifiers. -
#each_pair {|key, value| ... } ⇒ self
(also: #each_pair)
With a block given, calls the block with each key-value pair; returns
self: -
#each_key {|key| ... } ⇒ self
With a block given, calls the block with each key; returns
self: -
#each_pair {|key, value| ... } ⇒ self
Alias for #each.
-
#each_value {|value| ... } ⇒ self
With a block given, calls the block with each value; returns
self: -
#eql?(object) ⇒ Boolean
Returns
trueif all of the following are true: - #except(*keys) ⇒ Hash
-
#fetch(key) ⇒ Object
With no block given, returns the value for the given #key, if found;.
- #fetch_values(*keys) ⇒ Array
-
#select {|key, value| ... } ⇒ Hash
(also: #select)
With a block given, calls the block with each entry’s key and value; returns a new hash whose entries are those for which the block returns a truthy value:
-
#select! {|key, value| ... } ⇒ self?
(also: #select!)
With a block given, calls the block with each entry’s key and value; removes from
selfeach entry for which the block returnsfalseornil. -
#flatten(depth = 1) ⇒ Array
With positive integer
depth, returns a new array that is a recursive flattening ofselfto the givendepth. -
#has_key?(key) ⇒ Boolean
Alias for #key?.
-
#has_value?(value) ⇒ Boolean
Alias for #value?.
-
#hash ⇒ Integer
Returns the integer hash-code for the hash.
-
#include?(key) ⇒ Boolean
Alias for #key?.
-
#initialize_copy(other_hash) ⇒ self
Alias for #replace.
-
#inspect ⇒ String
Alias for #to_s.
-
#invert ⇒ Hash
Returns a new hash with each key-value pair inverted:
-
#keep_if {|key, value| ... } ⇒ self
With a block given, calls the block for each key-value pair; retains the entry if the block returns a truthy value; otherwise deletes the entry; returns
self: -
#key(value) ⇒ key?
Returns the key for the first-found entry with the given
value(see Entry Order): -
#key?(key) ⇒ Boolean
(also: #include?, #member?, #has_key?)
Returns whether #key is a key in
self: -
#keys ⇒ Array
Returns a new array containing all keys in
self: -
#length ⇒ Integer
(also: #size)
Returns the count of entries in
self: -
#member?(key) ⇒ Boolean
Alias for #key?.
-
#merge(*other_hashes) ⇒ Hash
Each argument
other_hashinother_hashesmust be a hash. -
#update(*other_hashes) ⇒ self
(also: #update)
Updates values and/or adds entries to
self; returnsself. -
#rassoc(value) ⇒ Array?
Searches
selffor the first entry whose value is #== to the givenvalue; see Entry Order. -
#rehash ⇒ self
Rebuilds the hash table for
selfby recomputing the hash index for each key; returnsself. -
#reject {|key, value| ... } ⇒ Hash
With a block given, returns a copy of
selfwith zero or more entries removed; calls the block with each key-value pair; excludes the entry in the copy if the block returns a truthy value, includes it otherwise: -
#reject! {|key, value| ... } ⇒ self?
With a block given, calls the block with each entry’s key and value; removes the entry from
selfif the block returns a truthy value. -
#replace(other_hash) ⇒ self
(also: #initialize_copy)
Replaces the entire contents of
selfwith the contents ofother_hash; returnsself: -
#select {|key, value| ... } ⇒ Hash
Alias for #filter.
-
#select! {|key, value| ... } ⇒ self?
Alias for #filter!.
-
#shift ⇒ Array, value
Removes and returns the first entry of
selfas a 2-element array; see Entry Order: -
#size ⇒ Integer
Alias for #length.
-
#slice(*keys) ⇒ Hash
Returns a new hash containing the entries from
selffor the given #keys; ignores any keys that are not found: -
#store(key, object) ⇒ Object
Alias for #[]=.
-
#to_a ⇒ Array
Returns all elements of
selfas an array of 2-element arrays; each nested array contains a key-value pair fromself: -
#to_h {|key, value| ... } ⇒ Hash
With a block given, returns a new hash whose content is based on the block; the block is called with each entry’s key and value; the block should return a 2-element array containing the key and value to be included in the returned array:
-
#to_hash ⇒ self
Returns
self. -
#to_proc ⇒ Proc
Returns a
::Procobject that maps a key to its value: -
#to_s ⇒ String
(also: #inspect)
Returns a new string containing the hash entries:
-
#transform_keys {|old_key| ... } ⇒ Hash
With an argument, a block, or both given, derives a new hash
new_hashfromself, the argument, and/or the block; all, some, or none of its keys may be different from those inself. -
#transform_keys! {|old_key| ... } ⇒ self
With an argument, a block, or both given, derives keys from the argument, the block, and
self; all, some, or none of the keys inselfmay be changed. -
#transform_values {|value| ... } ⇒ Hash
With a block given, returns a new hash
new_hash; for each pairkey+/+valueinself, calls the block withvalueand captures its return asnew_value; adds tonew_hashthe entrykey+/+new_value: -
#transform_values! {|old_value| ... } ⇒ self
With a block given, changes the values of
selfas determined by the block; returnsself. -
#update(*other_hashes) ⇒ self
Alias for #merge!.
-
#value?(value) ⇒ Boolean
(also: #has_value?)
Returns whether
valueis a value inself. -
#values ⇒ Array
Returns a new array containing all values in
self: -
#values_at(*keys) ⇒ Array
Returns a new array containing values for the given #keys:
- #deconstruct_keys(keys) Internal use only
- #freeze Internal use only
::Enumerable - Included
| #all? | Returns whether every element meets a given criterion. |
| #any? | Returns whether any element meets a given criterion. |
| #chain | Returns an enumerator object generated from this enumerator and given enumerables. |
| #chunk | Each element in the returned enumerator is a 2-element array consisting of: |
| #chunk_while | Creates an enumerator for each chunked elements. |
| #collect | Alias for Enumerable#map. |
| #collect_concat | Alias for Enumerable#flat_map. |
| #compact | Returns an array of all non- |
| #count | Returns the count of elements, based on an argument or block criterion, if given. |
| #cycle | When called with positive integer argument |
| #detect | Alias for Enumerable#find. |
| #drop | For positive integer |
| #drop_while | Calls the block with successive elements as long as the block returns a truthy value; returns an array of all elements after that point: |
| #each_cons | Calls the block with each successive overlapped |
| #each_entry | Calls the given block with each element, converting multiple values from yield to an array; returns |
| #each_slice | Calls the block with each successive disjoint |
| #each_with_index | Invoke |
| #each_with_object | Calls the block once for each element, passing both the element and the given object: |
| #entries | Alias for Enumerable#to_a. |
| #filter | Returns an array containing elements selected by the block. |
| #filter_map | Returns an array containing truthy elements returned by the block. |
| #find | Returns the first element for which the block returns a truthy value. |
| #find_all | Alias for Enumerable#filter. |
| #find_index | Returns the index of the first element that meets a specified criterion, or |
| #first | Returns the first element or elements. |
| #flat_map | Returns an array of flattened objects returned by the block. |
| #grep | Returns an array of objects based elements of |
| #grep_v | Returns an array of objects based on elements of |
| #group_by | With a block given returns a hash: |
| #include? | Alias for Enumerable#member?. |
| #inject | Returns the result of applying a reducer to an initial value and the first element of the |
| #lazy | Returns an |
| #map | Returns an array of objects returned by the block. |
| #max | Returns the element with the maximum element according to a given criterion. |
| #max_by | Returns the elements for which the block returns the maximum values. |
| #member? | Returns whether for any element |
| #min | Returns the element with the minimum element according to a given criterion. |
| #min_by | Returns the elements for which the block returns the minimum values. |
| #minmax | Returns a 2-element array containing the minimum and maximum elements according to a given criterion. |
| #minmax_by | Returns a 2-element array containing the elements for which the block returns minimum and maximum values: |
| #none? | Returns whether no element meets a given criterion. |
| #one? | Returns whether exactly one element meets a given criterion. |
| #partition | With a block given, returns an array of two arrays: |
| #reduce | Alias for Enumerable#inject. |
| #reject | Returns an array of objects rejected by the block. |
| #reverse_each | With a block given, calls the block with each element, but in reverse order; returns |
| #select | Alias for Enumerable#filter. |
| #slice_after | Creates an enumerator for each chunked elements. |
| #slice_before | With argument |
| #slice_when | Creates an enumerator for each chunked elements. |
| #sort | Returns an array containing the sorted elements of |
| #sort_by | With a block given, returns an array of elements of |
| #sum | With no block given, returns the sum of |
| #take | For non-negative integer |
| #take_while | Calls the block with successive elements as long as the block returns a truthy value; returns an array of all elements up to that point: |
| #tally | When argument #hash is not given, returns a new hash whose keys are the distinct elements in |
| #to_a | Returns an array containing the items in |
| #to_h | When |
| #to_set | Makes a set from the enumerable object with given arguments. |
| #uniq | With no block, returns a new array containing only unique elements; the array has no two elements |
| #zip | With no block given, returns a new array |
Constructor Details
.new(default_value = nil, capacity: 0) ⇒ Hash
.new(capacity: 0) {|self, key| ... } ⇒ Hash
Hash
.new(capacity: 0) {|self, key| ... } ⇒ Hash
Returns a new empty Hash object.
Initializes the values of #default and #default_proc, which determine the behavior when a given key is not found; see Key Not Found?.
By default, a hash has nil values for both #default and #default_proc:
h = Hash.new # => {}
h.default # => nil
h.default_proc # => nil
With argument default_value given, sets the #default value for the hash:
h = Hash.new(false) # => {}
h.default # => false
h.default_proc # => nil
With a block given, sets the #default_proc value:
h = Hash.new {|hash, key| "Hash #{hash}: Default value for #{key}" }
h.default # => nil
h.default_proc # => #<Proc:0x00000289b6fa7048 (irb):185>
h[:nosuch] # => "Hash {}: Default value for nosuch"
Raises ArgumentError if both default_value and a block are given.
If optional keyword argument capacity is given with a positive integer value n, initializes the hash with enough capacity to accommodate n entries without resizing.
See also Methods for Creating a Hash.
# File 'hash.rb', line 37
def initialize(ifnone = (ifnone_unset = true), capacity: 0, &block) Primitive.rb_hash_init(capacity, ifnone_unset, ifnone, block) end
Class Method Details
.[] ⇒ Hash
.[](other_hash) ⇒ Hash
.[]([*2_element_arrays] ) ⇒ Hash
.[](*objects) ⇒ Hash
Hash
.[](other_hash) ⇒ Hash
.[]([*2_element_arrays] ) ⇒ Hash
.[](*objects) ⇒ Hash
Returns a new Hash object populated with the given objects, if any. See .new.
With no argument given, returns a new empty hash.
With a single argument other_hash given that is a hash, returns a new hash initialized with the entries from that hash (but not with its #default or #default_proc):
h = {foo: 0, bar: 1, baz: 2}
Hash[h] # => {foo: 0, bar: 1, baz: 2}
With a single argument 2_element_arrays given that is an array of 2-element arrays, returns a new hash wherein each given 2-element array forms a key-value entry:
Hash[ [ [:foo, 0], [:, 1] ] ] # => {foo: 0, bar: 1}
With an even number of arguments objects given, returns a new hash wherein each successive pair of arguments is a key-value entry:
Hash[:foo, 0, :, 1] # => {foo: 0, bar: 1}
Raises ArgumentError if the argument list does not conform to any of the above.
See also Methods for Creating a Hash.
# File 'hash.c', line 1786
static VALUE
rb_hash_s_create(int argc, VALUE *argv, VALUE klass)
{
VALUE hash, tmp;
if (argc == 1) {
tmp = rb_hash_s_try_convert(Qnil, argv[0]);
if (!NIL_P(tmp)) {
if (!RHASH_EMPTY_P(tmp) && rb_hash_compare_by_id_p(tmp)) {
/* hash_copy for non-empty hash will copy compare_by_identity
flag, but we don't want it copied. Work around by
converting hash to flattened array and using that. */
tmp = rb_hash_to_a(tmp);
}
else {
hash = hash_alloc(klass);
if (!RHASH_EMPTY_P(tmp))
hash_copy(hash, tmp);
return hash;
}
}
else {
tmp = rb_check_array_type(argv[0]);
}
if (!NIL_P(tmp)) {
long i;
hash = hash_alloc(klass);
for (i = 0; i < RARRAY_LEN(tmp); ++i) {
VALUE e = RARRAY_AREF(tmp, i);
VALUE v = rb_check_array_type(e);
VALUE key, val = Qnil;
if (NIL_P(v)) {
rb_raise(rb_eArgError, "wrong element type %s at %ld (expected array)",
rb_builtin_class_name(e), i);
}
switch (RARRAY_LEN(v)) {
default:
rb_raise(rb_eArgError, "invalid number of elements (%ld for 1..2)",
RARRAY_LEN(v));
case 2:
val = RARRAY_AREF(v, 1);
case 1:
key = RARRAY_AREF(v, 0);
rb_hash_aset(hash, key, val);
}
}
return hash;
}
}
if (argc % 2 != 0) {
rb_raise(rb_eArgError, "odd number of arguments for Hash");
}
hash = hash_alloc(klass);
rb_hash_bulk_insert(argc, argv, hash);
hash_verify(hash);
return hash;
}
.ruby2_keywords_hash(hash) ⇒ Hash
Duplicates a given hash and adds a ruby2_keywords flag. This method is not for casual use; debugging, researching, and some truly necessary cases like deserialization of arguments.
h = {k: 1}
h = Hash.ruby2_keywords_hash(h)
def foo(k: 42)
k
end
foo(*[h]) #=> 1 with neither a warning or an error
# File 'hash.c', line 1916
static VALUE
rb_hash_s_ruby2_keywords_hash(VALUE dummy, VALUE hash)
{
Check_Type(hash, T_HASH);
VALUE tmp = rb_hash_dup(hash);
if (RHASH_EMPTY_P(hash) && rb_hash_compare_by_id_p(hash)) {
rb_hash_compare_by_id(tmp);
}
RHASH(tmp)->basic.flags |= RHASH_PASS_AS_KEYWORDS;
return tmp;
}
.ruby2_keywords_hash?(hash) ⇒ Boolean
Checks if a given hash is flagged by Module#ruby2_keywords (or Proc#ruby2_keywords). This method is not for casual use; debugging, researching, and some truly necessary cases like serialization of arguments.
ruby2_keywords def foo(*args)
Hash.ruby2_keywords_hash?(args.last)
end
foo(k: 1) #=> true
foo({k: 1}) #=> false
# File 'hash.c', line 1894
static VALUE
rb_hash_s_ruby2_keywords_hash_p(VALUE dummy, VALUE hash)
{
Check_Type(hash, T_HASH);
return RBOOL(RHASH(hash)->basic.flags & RHASH_PASS_AS_KEYWORDS);
}
.try_convert(object) ⇒ Object, ...
If object is a hash, returns object.
Otherwise if object responds to :to_hash, calls object.to_hash; returns the result if it is a hash, or raises ::TypeError if not.
Otherwise if object does not respond to :to_hash, returns nil.
# File 'hash.c', line 1873
static VALUE
rb_hash_s_try_convert(VALUE dummy, VALUE hash)
{
return rb_check_hash_type(hash);
}
Instance Attribute Details
#compare_by_identity ⇒ self (readonly)
Sets self to compare keys using identity (rather than mere equality); returns self:
By default, two keys are considered to be the same key if and only if they are equal objects (per method #eql?):
h = {}
h['x'] = 0
h['x'] = 1 # Overwrites.
h # => {"x"=>1}
When this method has been called, two keys are considered to be the same key if and only if they are the same object:
h.compare_by_identity
h['x'] = 2 # Does not overwrite.
h # => {"x"=>1, "x"=>2}
Related: #compare_by_identity?; see also Methods for Comparing.
# File 'hash.c', line 4639
VALUE
rb_hash_compare_by_id(VALUE hash)
{
VALUE tmp;
st_table *identtable;
if (rb_hash_compare_by_id_p(hash)) return hash;
rb_hash_modify_check(hash);
if (hash_iterating_p(hash)) {
rb_raise(rb_eRuntimeError, "compare_by_identity during iteration");
}
if (RHASH_TABLE_EMPTY_P(hash)) {
// Fast path: There's nothing to rehash, so we don't need a `tmp` table.
// We're most likely an AR table, so this will need an allocation.
ar_force_convert_table(hash, __FILE__, __LINE__);
HASH_ASSERT(RHASH_ST_TABLE_P(hash));
RHASH_ST_TABLE(hash)->type = &identhash;
}
else {
// Slow path: Need to rehash the members of `self` into a new
// `tmp` table using the new `identhash` compare/hash functions.
tmp = hash_alloc(0);
hash_st_table_init(tmp, &identhash, RHASH_SIZE(hash));
identtable = RHASH_ST_TABLE(tmp);
rb_hash_foreach(hash, rb_hash_rehash_i, (VALUE)tmp);
rb_hash_free(hash);
// We know for sure `identtable` is an st table,
// so we can skip `ar_force_convert_table` here.
RHASH_ST_TABLE_SET(hash, identtable);
RHASH_ST_CLEAR(tmp);
}
return hash;
}
#compare_by_identity? ⇒ Boolean (readonly)
Returns whether #compare_by_identity has been called:
h = {}
h.compare_by_identity? # => false
h.compare_by_identity
h.compare_by_identity? # => true
Related: #compare_by_identity; see also Methods for Comparing.
# File 'hash.c', line 4694
VALUE
rb_hash_compare_by_id_p(VALUE hash)
{
return RBOOL(RHASH_IDENTHASH_P(hash));
}
#default_proc ⇒ Proc? (rw)
Returns the default proc for self (see Hash Default):
h = {}
h.default_proc # => nil
h.default_proc = proc {|hash, key| "Default value for #{key}" }
h.default_proc.class # => Proc
# File 'hash.c', line 2234
static VALUE
rb_hash_default_proc(VALUE hash)
{
if (FL_TEST(hash, RHASH_PROC_DEFAULT)) {
return RHASH_IFNONE(hash);
}
return Qnil;
}
#default_proc=(proc) ⇒ Proc (rw)
Sets the default proc for self to proc (see Hash Default):
h = {}
h.default_proc # => nil
h.default_proc = proc { |hash, key| "Default value for #{key}" }
h.default_proc.class # => Proc
h.default_proc = nil
h.default_proc # => nil
# File 'hash.c', line 2257
VALUE
rb_hash_set_default_proc(VALUE hash, VALUE proc)
{
VALUE b;
rb_hash_modify_check(hash);
if (NIL_P(proc)) {
SET_DEFAULT(hash, proc);
return proc;
}
b = rb_check_convert_type_with_id(proc, T_DATA, "Proc", idTo_proc);
if (NIL_P(b) || !rb_obj_is_proc(b)) {
rb_raise(rb_eTypeError,
"wrong default_proc type %s (expected Proc)",
rb_obj_classname(proc));
}
proc = b;
SET_PROC_DEFAULT(hash, proc);
return proc;
}
#empty? ⇒ Boolean (readonly)
Returns true if there are no hash entries, false otherwise:
{}.empty? # => true
{foo: 0}.empty? # => false
Related: see Methods for Querying.
# File 'hash.c', line 3024
VALUE
rb_hash_empty_p(VALUE hash)
{
return RBOOL(RHASH_EMPTY_P(hash));
}
Instance Method Details
#<(other_hash) ⇒ Boolean
Returns true if the entries of self are a proper subset of the entries of other_hash, false otherwise:
h = {foo: 0, bar: 1}
h < {foo: 0, bar: 1, baz: 2} # => true # Proper subset.
h < {baz: 2, bar: 1, foo: 0} # => true # Order may differ.
h < h # => false # Not a proper subset.
h < {bar: 1, foo: 0} # => false # Not a proper subset.
h < {foo: 0, bar: 1, baz: 2} # => false # Different key.
h < {foo: 0, bar: 1, baz: 2} # => false # Different value.
See Hash Inclusion.
Raises TypeError if other_hash is not a hash and cannot be converted to a hash.
Related: see Methods for Comparing.
# File 'hash.c', line 4937
static VALUE
rb_hash_lt(VALUE hash, VALUE other)
{
other = to_hash(other);
if (RHASH_SIZE(hash) >= RHASH_SIZE(other)) return Qfalse;
return hash_le(hash, other);
}
#<=(other_hash) ⇒ Boolean
Returns true if the entries of self are a subset of the entries of other_hash, false otherwise:
h0 = {foo: 0, bar: 1}
h1 = {foo: 0, bar: 1, baz: 2}
h0 <= h0 # => true
h0 <= h1 # => true
h1 <= h0 # => false
See Hash Inclusion.
Raises TypeError if other_hash is not a hash and cannot be converted to a hash.
Related: see Methods for Comparing.
# File 'hash.c', line 4908
static VALUE
rb_hash_le(VALUE hash, VALUE other)
{
other = to_hash(other);
if (RHASH_SIZE(hash) > RHASH_SIZE(other)) return Qfalse;
return hash_le(hash, other);
}
#==(object) ⇒ Boolean
Returns whether self and object are equal.
Returns true if all of the following are true:
-
objectis aHashobject (or can be converted to one). -
selfandobjecthave the same keys (regardless of order). -
For each key #key,
self[key] == object[key].
Otherwise, returns false.
Examples:
h = {foo: 0, bar: 1}
h == {foo: 0, bar: 1} # => true # Equal entries (same order)
h == {bar: 1, foo: 0} # => true # Equal entries (different order).
h == 1 # => false # Object not a hash.
h == {} # => false # Different number of entries.
h == {foo: 0, bar: 1} # => false # Different key.
h == {foo: 0, bar: 1} # => false # Different value.
Related: see Methods for Comparing.
# File 'hash.c', line 4004
static VALUE
rb_hash_equal(VALUE hash1, VALUE hash2)
{
return hash_equal(hash1, hash2, FALSE);
}
#>(other_hash) ⇒ Boolean
Returns true if the entries of self are a proper superset of the entries of other_hash, false otherwise:
h = {foo: 0, bar: 1, baz: 2}
h > {foo: 0, bar: 1} # => true # Proper superset.
h > {bar: 1, foo: 0} # => true # Order may differ.
h > h # => false # Not a proper superset.
h > {baz: 2, bar: 1, foo: 0} # => false # Not a proper superset.
h > {foo: 0, bar: 1} # => false # Different key.
h > {foo: 0, bar: 1} # => false # Different value.
See Hash Inclusion.
Raises TypeError if other_hash is not a hash and cannot be converted to a hash.
Related: see Methods for Comparing.
# File 'hash.c', line 4993
static VALUE
rb_hash_gt(VALUE hash, VALUE other)
{
other = to_hash(other);
if (RHASH_SIZE(hash) <= RHASH_SIZE(other)) return Qfalse;
return hash_le(other, hash);
}
#>=(other_hash) ⇒ Boolean
Returns true if the entries of self are a superset of the entries of other_hash, false otherwise:
h0 = {foo: 0, bar: 1, baz: 2}
h1 = {foo: 0, bar: 1}
h0 >= h1 # => true
h0 >= h0 # => true
h1 >= h0 # => false
See Hash Inclusion.
Raises TypeError if other_hash is not a hash and cannot be converted to a hash.
Related: see Methods for Comparing.
# File 'hash.c', line 4964
static VALUE
rb_hash_ge(VALUE hash, VALUE other)
{
other = to_hash(other);
if (RHASH_SIZE(hash) < RHASH_SIZE(other)) return Qfalse;
return hash_le(other, hash);
}
#[](key) ⇒ Object
Searches for a hash key equivalent to the given #key; see Hash Key Equivalence.
If the key is found, returns its value:
{foo: 0, bar: 1, baz: 2}
h[:] # => 1
Otherwise, returns a default value (see Hash Default).
Related: #[]=; see also Methods for Fetching.
# File 'hash.c', line 2067
VALUE
rb_hash_aref(VALUE hash, VALUE key)
{
st_data_t val;
if (hash_stlike_lookup(hash, key, &val)) {
return (VALUE)val;
}
else {
return rb_hash_default_value(hash, key);
}
}
#[]=(key, object) ⇒ Object Also known as: #store
Associates the given object with the given #key; returns object.
Searches for a hash key equivalent to the given #key; see Hash Key Equivalence.
If the key is found, replaces its value with the given object; the ordering is not affected (see Entry Order):
h = {foo: 0, bar: 1}
h[:foo] = 2 # => 2
h[:foo] # => 2
If #key is not found, creates a new entry for the given #key and object; the new entry is last in the order (see Entry Order):
h = {foo: 0, bar: 1}
h[:baz] = 2 # => 2
h[:baz] # => 2
h # => {:foo=>0, :bar=>1, :baz=>2}
Related: #[]; see also Methods for Assigning.
# File 'hash.c', line 2928
VALUE
rb_hash_aset(VALUE hash, VALUE key, VALUE val)
{
bool iter_p = hash_iterating_p(hash);
rb_hash_modify(hash);
if (!RHASH_STRING_KEY_P(hash, key)) {
RHASH_UPDATE_ITER(hash, iter_p, key, hash_aset, val);
}
else {
RHASH_UPDATE_ITER(hash, iter_p, key, hash_aset_str, val);
}
return val;
}
#any? ⇒ Boolean
#any?(entry) ⇒ Boolean
#any? {|key, value| ... } ⇒ Boolean
Boolean
#any?(entry) ⇒ Boolean
#any? {|key, value| ... } ⇒ Boolean
Returns true if any element satisfies a given criterion; false otherwise.
If self has no element, returns false and argument or block are not used; otherwise behaves as below.
With no argument and no block, returns true if self is non-empty, false otherwise.
With argument entry and no block, returns true if for any key #key self.assoc(key) == entry, false otherwise:
h = {foo: 0, bar: 1, baz: 2}
h.assoc(:) # => [:bar, 1]
h.any?([:, 1]) # => true
h.any?([:, 0]) # => false
With no argument and a block given, calls the block with each key-value pair; returns true if the block returns a truthy value, false otherwise:
h = {foo: 0, bar: 1, baz: 2}
h.any? {|key, value| value < 3 } # => true
h.any? {|key, value| value > 3 } # => false
With both argument entry and a block given, issues a warning and ignores the block.
Related: Enumerable#any? (which this method overrides); see also Methods for Fetching.
# File 'hash.c', line 4795
static VALUE
rb_hash_any_p(int argc, VALUE *argv, VALUE hash)
{
VALUE args[2];
args[0] = Qfalse;
rb_check_arity(argc, 0, 1);
if (RHASH_EMPTY_P(hash)) return Qfalse;
if (argc) {
if (rb_block_given_p()) {
rb_warn("given block not used");
}
args[1] = argv[0];
rb_hash_foreach(hash, any_p_i_pattern, (VALUE)args);
}
else {
if (!rb_block_given_p()) {
/* yields pairs, never false */
return Qtrue;
}
if (rb_block_pair_yield_optimizable())
rb_hash_foreach(hash, any_p_i_fast, (VALUE)args);
else
rb_hash_foreach(hash, any_p_i, (VALUE)args);
}
return args[0];
}
#assoc(key) ⇒ entry?
If the given #key is found, returns its entry as a 2-element array containing that key and its value:
h = {foo: 0, bar: 1, baz: 2}
h.assoc(:) # => [:bar, 1]
Returns nil if the key is not found.
Related: see Methods for Fetching.
# File 'hash.c', line 4392
static VALUE
rb_hash_assoc(VALUE hash, VALUE key)
{
VALUE args[2];
if (RHASH_EMPTY_P(hash)) return Qnil;
if (RHASH_ST_TABLE_P(hash) && !RHASH_IDENTHASH_P(hash)) {
VALUE value = Qundef;
st_table assoctable = *RHASH_ST_TABLE(hash);
assoctable.type = &(struct st_hash_type){
.compare = assoc_cmp,
.hash = assoctable.type->hash,
};
VALUE arg = (VALUE)&(struct assoc_arg){
.tbl = &assoctable,
.key = (st_data_t)key,
};
if (RB_OBJ_FROZEN(hash)) {
value = assoc_lookup(arg);
}
else {
hash_iter_lev_inc(hash);
value = rb_ensure(assoc_lookup, arg, hash_foreach_ensure, hash);
}
hash_verify(hash);
if (!UNDEF_P(value)) return rb_assoc_new(key, value);
}
args[0] = key;
args[1] = Qnil;
rb_hash_foreach(hash, assoc_i, (VALUE)args);
return args[1];
}
#clear ⇒ self
Removes all entries from self; returns emptied self.
Related: see Methods for Deleting.
# File 'hash.c', line 2850
VALUE
rb_hash_clear(VALUE hash)
{
rb_hash_modify_check(hash);
if (hash_iterating_p(hash)) {
rb_hash_foreach(hash, clear_i, 0);
}
else if (RHASH_AR_TABLE_P(hash)) {
ar_clear(hash);
}
else {
st_clear(RHASH_ST_TABLE(hash));
compact_after_delete(hash);
}
return hash;
}
#compact ⇒ Hash
Returns a copy of self with all nil-valued entries removed:
h = {foo: 0, bar: nil, baz: 2, bat: nil}
h.compact # => {foo: 0, baz: 2}
Related: see Methods for Deleting.
# File 'hash.c', line 4569
static VALUE
rb_hash_compact(VALUE hash)
{
VALUE result = rb_hash_dup(hash);
if (!RHASH_EMPTY_P(hash)) {
rb_hash_foreach(result, delete_if_nil, result);
compact_after_delete(result);
}
else if (rb_hash_compare_by_id_p(hash)) {
result = rb_hash_compare_by_id(result);
}
return result;
}
#compact! ⇒ self?
If self contains any nil-valued entries, returns self with all nil-valued entries removed; returns nil otherwise:
h = {foo: 0, bar: nil, baz: 2, bat: nil}
h.compact!
h # => {foo: 0, baz: 2}
h.compact! # => nil
Related: see Methods for Deleting.
# File 'hash.c', line 4599
static VALUE
rb_hash_compact_bang(VALUE hash)
{
st_index_t n;
rb_hash_modify_check(hash);
n = RHASH_SIZE(hash);
if (n) {
rb_hash_foreach(hash, delete_if_nil, hash);
if (n != RHASH_SIZE(hash))
return hash;
}
return Qnil;
}
#deconstruct_keys(keys)
# File 'hash.c', line 5030
static VALUE
rb_hash_deconstruct_keys(VALUE hash, VALUE keys)
{
return hash;
}
Returns the default value for the given #key. The returned value will be determined either by the default proc or by the default value. See Hash Default.
With no argument, returns the current default value:
h = {}
h.default # => nil
If #key is given, returns the default value for #key, regardless of whether that key exists:
h = Hash.new { |hash, key| hash[key] = "No key #{key}"}
h[:foo] = "Hello"
h.default(:foo) # => "No key foo"
# File 'hash.c', line 2187
static VALUE
rb_hash_default(int argc, VALUE *argv, VALUE hash)
{
VALUE ifnone;
rb_check_arity(argc, 0, 1);
ifnone = RHASH_IFNONE(hash);
if (FL_TEST(hash, RHASH_PROC_DEFAULT)) {
if (argc == 0) return Qnil;
return call_default_proc(ifnone, hash, argv[0]);
}
return ifnone;
}
#default=(value) ⇒ Object
Sets the default value to value; returns value:
h = {}
h.default # => nil
h.default = false # => false
h.default # => false
See Hash Default.
# File 'hash.c', line 2214
VALUE
rb_hash_set_default(VALUE hash, VALUE ifnone)
{
rb_hash_modify_check(hash);
SET_DEFAULT(hash, ifnone);
return ifnone;
}
#delete(key) ⇒ value?
#delete(key) {|key| ... } ⇒ Object
value?
#delete(key) {|key| ... } ⇒ Object
If an entry for the given #key is found, deletes the entry and returns its associated value; otherwise returns nil or calls the given block.
With no block given and #key found, deletes the entry and returns its value:
h = {foo: 0, bar: 1, baz: 2}
h.delete(:) # => 1
h # => {foo: 0, baz: 2}
With no block given and #key not found, returns nil.
With a block given and #key found, ignores the block, deletes the entry, and returns its value:
h = {foo: 0, bar: 1, baz: 2}
h.delete(:baz) { |key| raise 'Will never happen'} # => 2
h # => {foo: 0, bar: 1}
With a block given and #key not found, calls the block and returns the block’s return value:
h = {foo: 0, bar: 1, baz: 2}
h.delete(:nosuch) { |key| "Key #{key} not found" } # => "Key nosuch not found"
h # => {foo: 0, bar: 1, baz: 2}
Related: see Methods for Deleting.
# File 'hash.c', line 2400
static VALUE
rb_hash_delete_m(VALUE hash, VALUE key)
{
VALUE val;
rb_hash_modify_check(hash);
val = rb_hash_delete_entry(hash, key);
if (!UNDEF_P(val)) {
compact_after_delete(hash);
return val;
}
else {
if (rb_block_given_p()) {
return rb_yield(key);
}
else {
return Qnil;
}
}
}
#delete_if {|key, value| ... } ⇒ self
#delete_if ⇒ Enumerator
self
#delete_if ⇒ Enumerator
With a block given, calls the block with each key-value pair, deletes each entry for which the block returns a truthy value, and returns self:
h = {foo: 0, bar: 1, baz: 2}
h.delete_if {|key, value| value > 0 } # => {foo: 0}
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2525
VALUE
rb_hash_delete_if(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_modify_check(hash);
if (!RHASH_TABLE_EMPTY_P(hash)) {
rb_hash_foreach(hash, delete_if_i, hash);
compact_after_delete(hash);
}
return hash;
}
#dig(key, *identifiers) ⇒ Object
Finds and returns an object found in nested objects, as specified by #key and identifiers.
The nested objects may be instances of various classes. See Dig Methods.
Nested hashes:
h = {foo: {bar: {baz: 2}}}
h.dig(:foo) # => {bar: {baz: 2}}
h.dig(:foo, :) # => {baz: 2}
h.dig(:foo, :, :baz) # => 2
h.dig(:foo, :, :BAZ) # => nil
Nested hashes and arrays:
h = {foo: {bar: [:a, :b, :c]}}
h.dig(:foo, :, 2) # => :c
If no such object is found, returns the hash default:
h = {foo: {bar: [:a, :b, :c]}}
h.dig(:hello) # => nil
h.default_proc = -> (hash, _key) { hash }
h.dig(:hello, :world)
# => {:foo=>{:bar=>[:a, :b, :c]}}
Related: Methods for Fetching.
# File 'hash.c', line 4859
static VALUE
rb_hash_dig(int argc, VALUE *argv, VALUE self)
{
rb_check_arity(argc, 1, UNLIMITED_ARGUMENTS);
self = rb_hash_aref(self, *argv);
if (!--argc) return self;
++argv;
return rb_obj_dig(argc, argv, self, Qnil);
}
#each_pair {|key, value| ... } ⇒ self
#each_pair ⇒ Enumerator
Also known as: #each_pair
self
#each_pair ⇒ Enumerator
With a block given, calls the block with each key-value pair; returns self:
h = {foo: 0, bar: 1, baz: 2}
h.each_pair {|key, value| puts "#{key}: #{value}"} # => {foo: 0, bar: 1, baz: 2}
Output:
foo: 0
: 1
baz: 2
With no block given, returns a new ::Enumerator.
Related: see Methods for Iterating.
# File 'hash.c', line 3137
static VALUE
rb_hash_each_pair(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
if (rb_block_pair_yield_optimizable())
rb_hash_foreach(hash, each_pair_i_fast, 0);
else
rb_hash_foreach(hash, each_pair_i, 0);
return hash;
}
#each_key {|key| ... } ⇒ self
#each_key ⇒ Enumerator
self
#each_key ⇒ Enumerator
With a block given, calls the block with each key; returns self:
h = {foo: 0, bar: 1, baz: 2}
h.each_key {|key| puts key } # => {foo: 0, bar: 1, baz: 2}
Output:
foo
baz
With no block given, returns a new ::Enumerator.
Related: see Methods for Iterating.
# File 'hash.c', line 3091
static VALUE
rb_hash_each_key(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_foreach(hash, each_key_i, 0);
return hash;
}
#each_pair {|key, value| ... } ⇒ self
#each_pair ⇒ Enumerator
self
#each_pair ⇒ Enumerator
Alias for #each.
#each_value {|value| ... } ⇒ self
#each_value ⇒ Enumerator
self
#each_value ⇒ Enumerator
With a block given, calls the block with each value; returns self:
h = {foo: 0, bar: 1, baz: 2}
h.each_value {|value| puts value } # => {foo: 0, bar: 1, baz: 2}
Output:
0
1
2
With no block given, returns a new ::Enumerator.
Related: see Methods for Iterating.
# File 'hash.c', line 3057
static VALUE
rb_hash_each_value(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_foreach(hash, each_value_i, 0);
return hash;
}
#eql?(object) ⇒ Boolean
Returns true if all of the following are true:
-
The given
objectis aHashobject. -
selfandobjecthave the same keys (regardless of order). -
For each key #key,
self[key].eql?(object[key]).
Otherwise, returns false.
h1 = {foo: 0, bar: 1, baz: 2}
h2 = {foo: 0, bar: 1, baz: 2}
h1.eql? h2 # => true
h3 = {baz: 2, bar: 1, foo: 0}
h1.eql? h3 # => true
Related: see Methods for Querying.
# File 'hash.c', line 4031
static VALUE
rb_hash_eql(VALUE hash1, VALUE hash2)
{
return hash_equal(hash1, hash2, TRUE);
}
#except(*keys) ⇒ Hash
Returns a copy of self that excludes entries for the given #keys; any #keys that are not found are ignored:
h = {foo:0, bar: 1, baz: 2} # => {:foo=>0, :bar=>1, :baz=>2}
h.except(:baz, :foo) # => {:bar=>1}
h.except(:, :nosuch) # => {:foo=>0, :baz=>2}
Related: see Methods for Deleting.
# File 'hash.c', line 2651
static VALUE
rb_hash_except(int argc, VALUE *argv, VALUE hash)
{
int i;
VALUE key, result;
result = hash_dup_with_compare_by_id(hash);
for (i = 0; i < argc; i++) {
key = argv[i];
rb_hash_delete(result, key);
}
compact_after_delete(result);
return result;
}
With no block given, returns the value for the given #key, if found;
h = {foo: 0, bar: 1, baz: 2}
h.fetch(:) # => 1
If the key is not found, returns default_value, if given, or raises ::KeyError otherwise:
h.fetch(:nosuch, :default) # => :default
h.fetch(:nosuch) # Raises KeyError.
With a block given, calls the block with #key and returns the block’s return value:
{}.fetch(:nosuch) {|key| "No key #{key}"} # => "No key nosuch"
Note that this method does not use the values of either #default or #default_proc.
Related: see Methods for Fetching.
# File 'hash.c', line 2125
static VALUE
rb_hash_fetch_m(int argc, VALUE *argv, VALUE hash)
{
VALUE key;
st_data_t val;
long block_given;
rb_check_arity(argc, 1, 2);
key = argv[0];
block_given = rb_block_given_p();
if (block_given && argc == 2) {
rb_warn("block supersedes default value argument");
}
if (hash_stlike_lookup(hash, key, &val)) {
return (VALUE)val;
}
else {
if (block_given) {
return rb_yield(key);
}
else if (argc == 1) {
VALUE desc = rb_protect(rb_inspect, key, 0);
if (NIL_P(desc)) {
desc = rb_any_to_s(key);
}
desc = rb_str_ellipsize(desc, 65);
rb_key_err_raise(rb_sprintf("key not found: %"PRIsVALUE, desc), hash, key);
}
else {
return argv[1];
}
}
}
When all given #keys are found, returns a new array containing the values associated with the given #keys:
h = {foo: 0, bar: 1, baz: 2}
h.fetch_values(:baz, :foo) # => [2, 0]
When any given #keys are not found and a block is given, calls the block with each unfound key and uses the block’s return value as the value for that key:
h.fetch_values(:, :foo, :bad, :bam) {|key| key.to_s}
# => [1, 0, "bad", "bam"]
When any given #keys are not found and no block is given, raises ::KeyError.
Related: see Methods for Fetching.
# File 'hash.c', line 2721
static VALUE
rb_hash_fetch_values(int argc, VALUE *argv, VALUE hash)
{
VALUE result = rb_ary_new2(argc);
long i;
for (i=0; i<argc; i++) {
rb_ary_push(result, rb_hash_fetch(hash, argv[i]));
}
return result;
}
#select {|key, value| ... } ⇒ Hash
#select ⇒ Enumerator
Also known as: #select
Hash
#select ⇒ Enumerator
With a block given, calls the block with each entry’s key and value; returns a new hash whose entries are those for which the block returns a truthy value:
h = {foo: 0, bar: 1, baz: 2}
h.select {|key, value| value < 2 } # => {foo: 0, bar: 1}
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2759
static VALUE
rb_hash_select(VALUE hash)
{
VALUE result;
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
result = hash_dup_with_compare_by_id(hash);
if (!RHASH_EMPTY_P(hash)) {
rb_hash_foreach(result, keep_if_i, result);
compact_after_delete(result);
}
return result;
}
#select! {|key, value| ... } ⇒ self?
#select! ⇒ Enumerator
Also known as: #select!
self?
#select! ⇒ Enumerator
With a block given, calls the block with each entry’s key and value; removes from self each entry for which the block returns false or nil.
Returns self if any entries were removed, nil otherwise:
h = {foo: 0, bar: 1, baz: 2}
h.select! {|key, value| value < 2 } # => {foo: 0, bar: 1}
h.select! {|key, value| value < 2 } # => nil
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2793
static VALUE
rb_hash_select_bang(VALUE hash)
{
st_index_t n;
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_modify_check(hash);
n = RHASH_SIZE(hash);
if (!n) return Qnil;
rb_hash_foreach(hash, keep_if_i, hash);
if (n == RHASH_SIZE(hash)) return Qnil;
return hash;
}
#flatten(depth = 1) ⇒ Array
With positive integer depth, returns a new array that is a recursive flattening of self to the given depth.
At each level of recursion:
-
Each element whose value is an array is “flattened” (that is, replaced by its individual array elements); see Array#flatten.
-
Each element whose value is not an array is unchanged. even if the value is an object that has instance method flatten (such as a hash).
Examples; note that entry foo: {bar: 1, baz: 2} is never flattened.
h = {foo: {bar: 1, baz: 2}, bat: [:bam, [:bap, [:bah]]]}
h.flatten(1) # => [:foo, {:bar=>1, :baz=>2}, :bat, [:bam, [:bap, [:bah]]]]
h.flatten(2) # => [:foo, {:bar=>1, :baz=>2}, :bat, :bam, [:bap, [:bah]]]
h.flatten(3) # => [:foo, {:bar=>1, :baz=>2}, :bat, :bam, :bap, [:bah]]
h.flatten(4) # => [:foo, {:bar=>1, :baz=>2}, :bat, :bam, :bap, :bah]
h.flatten(5) # => [:foo, {:bar=>1, :baz=>2}, :bat, :bam, :bap, :bah]
With negative integer depth, flattens all levels:
h.flatten(-1) # => [:foo, {:bar=>1, :baz=>2}, :bat, :bam, :bap, :bah]
With depth zero, returns the equivalent of #to_a:
h.flatten(0) # => [[:foo, {:bar=>1, :baz=>2}], [:bat, [:bam, [:bap, [:bah]]]]]
Related: see Methods for Converting.
# File 'hash.c', line 4515
static VALUE
rb_hash_flatten(int argc, VALUE *argv, VALUE hash)
{
VALUE ary;
rb_check_arity(argc, 0, 1);
if (argc) {
int level = NUM2INT(argv[0]);
if (level == 0) return rb_hash_to_a(hash);
ary = rb_ary_new_capa(RHASH_SIZE(hash) * 2);
rb_hash_foreach(hash, flatten_i, ary);
level--;
if (level > 0) {
VALUE ary_flatten_level = INT2FIX(level);
rb_funcallv(ary, id_flatten_bang, 1, &ary_flatten_level);
}
else if (level < 0) {
/* flatten recursively */
rb_funcallv(ary, id_flatten_bang, 0, 0);
}
}
else {
ary = rb_ary_new_capa(RHASH_SIZE(hash) * 2);
rb_hash_foreach(hash, flatten_i, ary);
}
return ary;
}
#freeze
# File 'hash.c', line 103
VALUE
rb_hash_freeze(VALUE hash)
{
return rb_obj_freeze(hash);
}
#key?(key) ⇒ Boolean
#has_key?(key) ⇒ Boolean
Boolean
#has_key?(key) ⇒ Boolean
Alias for #key?.
#value?(value) ⇒ Boolean
#has_value?(value) ⇒ Boolean
Boolean
#has_value?(value) ⇒ Boolean
Alias for #value?.
#hash ⇒ Integer
Returns the integer hash-code for the hash.
Two hashes have the same hash-code if their content is the same (regardless of order):
h1 = {foo: 0, bar: 1, baz: 2}
h2 = {baz: 2, bar: 1, foo: 0}
h2.hash == h1.hash # => true
h2.eql? h1 # => true
Related: see Methods for Querying.
# File 'hash.c', line 4066
static VALUE
rb_hash_hash(VALUE hash)
{
st_index_t size = RHASH_SIZE(hash);
st_index_t hval = rb_hash_start(size);
hval = rb_hash_uint(hval, (st_index_t)rb_hash_hash);
if (size) {
rb_hash_foreach(hash, hash_i, (VALUE)&hval);
}
hval = rb_hash_end(hval);
return ST2FIX(hval);
}
#key?(key) ⇒ Boolean
#include?(key) ⇒ Boolean
Boolean
#include?(key) ⇒ Boolean
Alias for #key?.
#replace(other_hash) ⇒ self
#initialize_copy(other_hash) ⇒ self
self
#initialize_copy(other_hash) ⇒ self
Alias for #replace.
Alias for #to_s.
#invert ⇒ Hash
Returns a new hash with each key-value pair inverted:
h = {foo: 0, bar: 1, baz: 2}
h1 = h.invert
h1 # => {0=>:foo, 1=>:bar, 2=>:baz}
Overwrites any repeated new keys (see Entry Order):
h = {foo: 0, bar: 0, baz: 0}
h.invert # => {0=>:baz}
Related: see Methods for Transforming Keys and Values.
# File 'hash.c', line 4105
static VALUE
rb_hash_invert(VALUE hash)
{
VALUE h = rb_hash_new_with_size(RHASH_SIZE(hash));
rb_hash_foreach(hash, rb_hash_invert_i, h);
return h;
}
#keep_if {|key, value| ... } ⇒ self
#keep_if ⇒ Enumerator
self
#keep_if ⇒ Enumerator
With a block given, calls the block for each key-value pair; retains the entry if the block returns a truthy value; otherwise deletes the entry; returns self:
h = {foo: 0, bar: 1, baz: 2}
h.keep_if { |key, value| key.start_with?('b') } # => {bar: 1, baz: 2}
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2824
static VALUE
rb_hash_keep_if(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_modify_check(hash);
if (!RHASH_TABLE_EMPTY_P(hash)) {
rb_hash_foreach(hash, keep_if_i, hash);
}
return hash;
}
#key(value) ⇒ key?
Returns the key for the first-found entry with the given value (see Entry Order):
h = {foo: 0, bar: 2, baz: 2}
h.key(0) # => :foo
h.key(2) # => :bar
Returns nil if no such value is found.
Related: see Methods for Fetching.
# File 'hash.c', line 2306
static VALUE
rb_hash_key(VALUE hash, VALUE value)
{
VALUE args[2];
args[0] = value;
args[1] = Qnil;
rb_hash_foreach(hash, key_i, (VALUE)args);
return args[1];
}
#key?(key) ⇒ Boolean Also known as: #include?, #member?, #has_key?
Returns whether #key is a key in self:
h = {foo: 0, bar: 1, baz: 2}
h.include?(:) # => true
h.include?(:BAR) # => false
Related: Methods for Querying.
# File 'hash.c', line 3858
VALUE
rb_hash_has_key(VALUE hash, VALUE key)
{
return RBOOL(hash_stlike_lookup(hash, key, NULL));
}
#keys ⇒ Array
Returns a new array containing all keys in self:
h = {foo: 0, bar: 1, baz: 2}
h.keys # => [:foo, :bar, :baz]
Related: see Methods for Fetching.
# File 'hash.c', line 3766
VALUE
rb_hash_keys(VALUE hash)
{
st_index_t size = RHASH_SIZE(hash);
VALUE keys = rb_ary_new_capa(size);
if (size == 0) return keys;
if (ST_DATA_COMPATIBLE_P(VALUE)) {
RARRAY_PTR_USE(keys, ptr, {
if (RHASH_AR_TABLE_P(hash)) {
size = ar_keys(hash, ptr, size);
}
else {
st_table *table = RHASH_ST_TABLE(hash);
size = st_keys(table, ptr, size);
}
});
rb_gc_writebarrier_remember(keys);
rb_ary_set_len(keys, size);
}
else {
rb_hash_foreach(hash, keys_i, keys);
}
return keys;
}
#length ⇒ Integer Also known as: #size
Returns the count of entries in self:
{foo: 0, bar: 1, baz: 2}.size # => 3
Related: see Methods for Querying.
# File 'hash.c', line 3000
VALUE
rb_hash_size(VALUE hash)
{
return INT2FIX(RHASH_SIZE(hash));
}
#key?(key) ⇒ Boolean
#member?(key) ⇒ Boolean
Boolean
#member?(key) ⇒ Boolean
Alias for #key?.
#merge(*other_hashes) ⇒ Hash
#merge(*other_hashes) {|key, old_value, new_value| ... } ⇒ Hash
Hash
#merge(*other_hashes) {|key, old_value, new_value| ... } ⇒ Hash
Each argument other_hash in other_hashes must be a hash.
With arguments other_hashes given and no block, returns the new hash formed by merging each successive other_hash into a copy of self; returns that copy; for each successive entry in other_hash:
-
For a new key, the entry is added at the end of
self. -
For duplicate key, the entry overwrites the entry in
self, whose position is unchanged.
Example:
h = {foo: 0, bar: 1, baz: 2}
h1 = {bat: 3, bar: 4}
h2 = {bam: 5, bat:6}
h.merge(h1, h2) # => {foo: 0, bar: 4, baz: 2, bat: 6, bam: 5}
With arguments other_hashes and a block given, behaves as above except that for a duplicate key the overwriting entry takes it value not from the entry in other_hash, but instead from the block:
-
The block is called with the duplicate key and the values from both
selfandother_hash. -
The block’s return value becomes the new value for the entry in
self.
Example:
h = {foo: 0, bar: 1, baz: 2}
h1 = {bat: 3, bar: 4}
h2 = {bam: 5, bat:6}
h.merge(h1, h2) { |key, old_value, new_value| old_value + new_value }
# => {foo: 0, bar: 5, baz: 2, bat: 9, bam: 5}
With no arguments, returns a copy of self; the block, if given, is ignored.
Related: see Methods for Assigning.
# File 'hash.c', line 4339
static VALUE
rb_hash_merge(int argc, VALUE *argv, VALUE self)
{
return rb_hash_update(argc, argv, copy_compare_by_id(rb_hash_dup(self), self));
}
#update(*other_hashes) ⇒ self
#update(*other_hashes) {|key, old_value, new_value| ... } ⇒ self
Also known as: #update
self
#update(*other_hashes) {|key, old_value, new_value| ... } ⇒ self
Updates values and/or adds entries to self; returns self.
Each argument other_hash in other_hashes must be a hash.
With no block given, for each successive entry key+/+new_value in each successive other_hash:
-
If #key is in
self, setsself[key] = new_value, whose position is unchanged:h0 = {foo: 0, bar: 1, baz: 2} h1 = {bar: 3, foo: -1} h0.update(h1) # => {foo: -1, bar: 3, baz: 2} -
If #key is not in
self, adds the entry at the end ofself:h = {foo: 0, bar: 1, baz: 2} h.update({bam: 3, bah: 4}) # => {foo: 0, bar: 1, baz: 2, bam: 3, bah: 4}
With a block given, for each successive entry key+/+new_value in each successive other_hash:
-
If #key is in
self, fetchesold_valuefromself[key], calls the block with #key,old_value, andnew_value, and setsself[key] = new_value, whose position is unchanged :season = {AB: 75, H: 20, HR: 3, SO: 17, W: 11, HBP: 3} today = {AB: 3, H: 1, W: 1} yesterday = {AB: 4, H: 2, HR: 1} season.update(yesterday, today) {|key, old_value, new_value| old_value + new_value } # => {AB: 82, H: 23, HR: 4, SO: 17, W: 12, HBP: 3} -
If #key is not in
self, adds the entry at the end ofself:h = {foo: 0, bar: 1, baz: 2} h.update({bat: 3}) { fail 'Cannot happen' } # => {foo: 0, bar: 1, baz: 2, bat: 3}
Related: see Methods for Assigning.
# File 'hash.c', line 4228
static VALUE
rb_hash_update(int argc, VALUE *argv, VALUE self)
{
struct update_call_args args = {
.hash = self,
.argv = argv,
.argc = argc,
.block_given = rb_block_given_p(),
.iterating = false,
};
VALUE arg = (VALUE)&args;
rb_hash_modify(self);
return rb_ensure(rb_hash_update_call, arg, rb_hash_update_ensure, arg);
}
#rassoc(value) ⇒ Array?
Searches self for the first entry whose value is #== to the given value; see Entry Order.
If the entry is found, returns its key and value as a 2-element array; returns nil if not found:
h = {foo: 0, bar: 1, baz: 1}
h.rassoc(1) # => [:bar, 1]
Related: see Methods for Fetching.
# File 'hash.c', line 4456
static VALUE
rb_hash_rassoc(VALUE hash, VALUE obj)
{
VALUE args[2];
args[0] = obj;
args[1] = Qnil;
rb_hash_foreach(hash, rassoc_i, (VALUE)args);
return args[1];
}
#rehash ⇒ self
Rebuilds the hash table for self by recomputing the hash index for each key; returns self. Calling this method ensures that the hash table is valid.
The hash table becomes invalid if the hash value of a key has changed after the entry was created. See Modifying an Active Hash Key.
# File 'hash.c', line 1958
VALUE
rb_hash_rehash(VALUE hash)
{
VALUE tmp;
st_table *tbl;
if (hash_iterating_p(hash)) {
rb_raise(rb_eRuntimeError, "rehash during iteration");
}
rb_hash_modify_check(hash);
if (RHASH_AR_TABLE_P(hash)) {
tmp = hash_alloc(0);
rb_hash_foreach(hash, rb_hash_rehash_i, (VALUE)tmp);
hash_ar_free_and_clear_table(hash);
ar_copy(hash, tmp);
}
else if (RHASH_ST_TABLE_P(hash)) {
st_table *old_tab = RHASH_ST_TABLE(hash);
tmp = hash_alloc(0);
hash_st_table_init(tmp, old_tab->type, old_tab->num_entries);
tbl = RHASH_ST_TABLE(tmp);
rb_hash_foreach(hash, rb_hash_rehash_i, (VALUE)tmp);
hash_st_free(hash);
RHASH_ST_TABLE_SET(hash, tbl);
RHASH_ST_CLEAR(tmp);
}
hash_verify(hash);
return hash;
}
#reject {|key, value| ... } ⇒ Hash
#reject ⇒ Enumerator
Hash
#reject ⇒ Enumerator
With a block given, returns a copy of self with zero or more entries removed; calls the block with each key-value pair; excludes the entry in the copy if the block returns a truthy value, includes it otherwise:
h = {foo: 0, bar: 1, baz: 2}
h.reject {|key, value| key.start_with?('b') }
# => {foo: 0}
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2589
static VALUE
rb_hash_reject(VALUE hash)
{
VALUE result;
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
result = hash_dup_with_compare_by_id(hash);
if (!RHASH_EMPTY_P(hash)) {
rb_hash_foreach(result, delete_if_i, result);
compact_after_delete(result);
}
return result;
}
#reject! {|key, value| ... } ⇒ self?
#reject! ⇒ Enumerator
self?
#reject! ⇒ Enumerator
With a block given, calls the block with each entry’s key and value; removes the entry from self if the block returns a truthy value.
Return self if any entries were removed, nil otherwise:
h = {foo: 0, bar: 1, baz: 2}
h.reject! {|key, value| value < 2 } # => {baz: 2}
h.reject! {|key, value| value < 2 } # => nil
With no block given, returns a new ::Enumerator.
Related: see Methods for Deleting.
# File 'hash.c', line 2556
static VALUE
rb_hash_reject_bang(VALUE hash)
{
st_index_t n;
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_modify(hash);
n = RHASH_SIZE(hash);
if (!n) return Qnil;
rb_hash_foreach(hash, delete_if_i, hash);
if (n == RHASH_SIZE(hash)) return Qnil;
return hash;
}
#replace(other_hash) ⇒ self Also known as: #initialize_copy
Replaces the entire contents of self with the contents of other_hash; returns self:
h = {foo: 0, bar: 1, baz: 2}
h.replace({bat: 3, bam: 4}) # => {bat: 3, bam: 4}
Also replaces the default value or proc of self with the default value or proc of other_hash.
h = {}
other = Hash.new(:ok)
h.replace(other)
h.default # => :ok
Related: see Methods for Assigning.
# File 'hash.c', line 2965
static VALUE
rb_hash_replace(VALUE hash, VALUE hash2)
{
rb_hash_modify_check(hash);
if (hash == hash2) return hash;
if (hash_iterating_p(hash)) {
rb_raise(rb_eRuntimeError, "can't replace hash during iteration");
}
hash2 = to_hash(hash2);
COPY_DEFAULT(hash, hash2);
if (RHASH_AR_TABLE_P(hash)) {
hash_ar_free_and_clear_table(hash);
}
else {
hash_st_free_and_clear_table(hash);
}
hash_copy(hash, hash2);
return hash;
}
#select {|key, value| ... } ⇒ Hash
#select ⇒ Enumerator
Hash
#select ⇒ Enumerator
Alias for #filter.
#select! {|key, value| ... } ⇒ self?
#select! ⇒ Enumerator
self?
#select! ⇒ Enumerator
Alias for #filter!.
#shift ⇒ Array, value
Removes and returns the first entry of self as a 2-element array; see Entry Order:
h = {foo: 0, bar: 1, baz: 2}
h.shift # => [:foo, 0]
h # => {bar: 1, baz: 2}
Returns nil if self is empty.
Related: see Methods for Deleting.
# File 'hash.c', line 2453
static VALUE
rb_hash_shift(VALUE hash)
{
struct shift_var var;
rb_hash_modify_check(hash);
if (RHASH_AR_TABLE_P(hash)) {
var.key = Qundef;
if (!hash_iterating_p(hash)) {
if (ar_shift(hash, &var.key, &var.val)) {
return rb_assoc_new(var.key, var.val);
}
}
else {
rb_hash_foreach(hash, shift_i_safe, (VALUE)&var);
if (!UNDEF_P(var.key)) {
rb_hash_delete_entry(hash, var.key);
return rb_assoc_new(var.key, var.val);
}
}
}
if (RHASH_ST_TABLE_P(hash)) {
var.key = Qundef;
if (!hash_iterating_p(hash)) {
if (st_shift(RHASH_ST_TABLE(hash), &var.key, &var.val)) {
return rb_assoc_new(var.key, var.val);
}
}
else {
rb_hash_foreach(hash, shift_i_safe, (VALUE)&var);
if (!UNDEF_P(var.key)) {
rb_hash_delete_entry(hash, var.key);
return rb_assoc_new(var.key, var.val);
}
}
}
return Qnil;
}
Alias for #length.
#slice(*keys) ⇒ Hash
Returns a new hash containing the entries from self for the given #keys; ignores any keys that are not found:
h = {foo: 0, bar: 1, baz: 2}
h.slice(:baz, :foo, :nosuch) # => {baz: 2, foo: 0}
Related: see Methods for Deleting.
# File 'hash.c', line 2616
static VALUE
rb_hash_slice(int argc, VALUE *argv, VALUE hash)
{
int i;
VALUE key, value, result;
if (argc == 0 || RHASH_EMPTY_P(hash)) {
return copy_compare_by_id(rb_hash_new(), hash);
}
result = copy_compare_by_id(rb_hash_new_with_size(argc), hash);
for (i = 0; i < argc; i++) {
key = argv[i];
value = rb_hash_lookup2(hash, key, Qundef);
if (!UNDEF_P(value))
rb_hash_aset(result, key, value);
}
return result;
}
Alias for #[]=.
#to_a ⇒ Array
Returns all elements of self as an array of 2-element arrays; each nested array contains a key-value pair from self:
h = {foo: 0, bar: 1, baz: 2}
h.to_a # => [[:foo, 0], [:bar, 1], [:baz, 2]]
Related: see Methods for Converting.
# File 'hash.c', line 3558
static VALUE
rb_hash_to_a(VALUE hash)
{
VALUE ary;
ary = rb_ary_new_capa(RHASH_SIZE(hash));
rb_hash_foreach(hash, to_a_i, ary);
return ary;
}
#to_h {|key, value| ... } ⇒ Hash
#to_h ⇒ self, Hash
Hash
#to_h ⇒ self, Hash
With a block given, returns a new hash whose content is based on the block; the block is called with each entry’s key and value; the block should return a 2-element array containing the key and value to be included in the returned array:
h = {foo: 0, bar: 1, baz: 2}
h.to_h {|key, value| [value, key] }
# => {0 => :foo, 1 => :bar, 2 => :baz}
With no block given, returns self if self is an instance of Hash; if self is a subclass of Hash, returns a new hash containing the content of self.
Related: see Methods for Converting.
# File 'hash.c', line 3734
static VALUE
rb_hash_to_h(VALUE hash)
{
if (rb_block_given_p()) {
return rb_hash_to_h_block(hash);
}
if (rb_obj_class(hash) != rb_cHash) {
const VALUE flags = RBASIC(hash)->flags;
hash = hash_dup(hash, rb_cHash, flags & RHASH_PROC_DEFAULT);
}
return hash;
}
#to_hash ⇒ self
Returns self.
Related: see Methods for Converting.
# File 'hash.c', line 3675
static VALUE
rb_hash_to_hash(VALUE hash)
{
return hash;
}
#to_proc ⇒ Proc
Returns a ::Proc object that maps a key to its value:
h = {foo: 0, bar: 1, baz: 2}
proc = h.to_proc
proc.class # => Proc
proc.call(:foo) # => 0
proc.call(:) # => 1
proc.call(:nosuch) # => nil
Related: see Methods for Converting.
# File 'hash.c', line 5023
static VALUE
rb_hash_to_proc(VALUE hash)
{
return rb_func_lambda_new(hash_proc_call, hash, 1, 1);
}
#to_s ⇒ String Also known as: #inspect
Returns a new string containing the hash entries:
h = {foo: 0, bar: 1, baz: 2}
h.inspect # => "{foo: 0, bar: 1, baz: 2}"
Related: see Methods for Converting.
# File 'hash.c', line 3659
static VALUE
rb_hash_inspect(VALUE hash)
{
if (RHASH_EMPTY_P(hash))
return rb_usascii_str_new2("{}");
return rb_exec_recursive(inspect_hash, hash, 0);
}
#transform_keys {|old_key| ... } ⇒ Hash
#transform_keys(other_hash) ⇒ Hash
#transform_keys(other_hash) {|old_key| ... } ⇒ Hash
#transform_keys ⇒ Enumerator
Hash
#transform_keys(other_hash) ⇒ Hash
#transform_keys(other_hash) {|old_key| ... } ⇒ Hash
#transform_keys ⇒ Enumerator
With an argument, a block, or both given, derives a new hash new_hash from self, the argument, and/or the block; all, some, or none of its keys may be different from those in self.
With a block given and no argument, new_hash has keys determined only by the block.
For each key/value pair old_key/value in self, calls the block with old_key; the block’s return value becomes new_key; sets new_hash[new_key] = value; a duplicate key overwrites:
h = {foo: 0, bar: 1, baz: 2}
h.transform_keys {|old_key| old_key.to_s }
# => {"foo" => 0, "bar" => 1, "baz" => 2}
h.transform_keys {|old_key| 'xxx' }
# => {"xxx" => 2}
With argument other_hash given and no block, new_hash may have new keys provided by other_hash and unchanged keys provided by self.
For each key/value pair old_key/old_value in self, looks for key old_key in other_hash:
-
If
old_keyis found, its valueother_hash[old_key]is taken asnew_key; setsnew_hash[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys(baz: :BAZ, bar: :BAR, foo: :FOO) # => {FOO: 0, BAR: 1, BAZ: 2} h.transform_keys(baz: :FOO, bar: :FOO, foo: :FOO) # => {FOO: 2} -
If
old_keyis not found, setsnew_hash[old_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys({}) # => {foo: 0, bar: 1, baz: 2} h.transform_keys(baz: :foo) # => {foo: 2, bar: 1}
Unused keys in other_hash are ignored:
h = {foo: 0, bar: 1, baz: 2}
h.transform_keys(bat: 3)
# => {foo: 0, bar: 1, baz: 2}
With both argument other_hash and a block given, new_hash has new keys specified by other_hash or by the block, and unchanged keys provided by self.
For each pair old_key and value in self:
-
If
other_hashhas keyold_key(with valuenew_key), does not call the block for that key; setsnew_hash[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys(baz: :BAZ, bar: :BAR, foo: :FOO) {|key| fail 'Not called' } # => {FOO: 0, BAR: 1, BAZ: 2} -
If
other_hashdoes not have keyold_key, calls the block withold_keyand takes its return value asnew_key; setsnew_hash[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys(baz: :BAZ) {|key| key.to_s.reverse } # => {"oof" => 0, "rab" => 1, BAZ: 2} h.transform_keys(baz: :BAZ) {|key| 'ook' } # => {"ook" => 1, BAZ: 2}
With no argument and no block given, returns a new ::Enumerator.
Related: see Methods for Transforming Keys and Values.
# File 'hash.c', line 3266
static VALUE
rb_hash_transform_keys(int argc, VALUE *argv, VALUE hash)
{
VALUE result;
struct transform_keys_args transarg = {0};
argc = rb_check_arity(argc, 0, 1);
if (argc > 0) {
transarg.trans = to_hash(argv[0]);
transarg.block_given = rb_block_given_p();
}
else {
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
}
result = rb_hash_new();
if (!RHASH_EMPTY_P(hash)) {
if (transarg.trans) {
transarg.result = result;
rb_hash_foreach(hash, transform_keys_hash_i, (VALUE)&transarg);
}
else {
rb_hash_foreach(hash, transform_keys_i, result);
}
}
return result;
}
#transform_keys! {|old_key| ... } ⇒ self
#transform_keys!(other_hash) ⇒ self
#transform_keys!(other_hash) {|old_key| ... } ⇒ self
#transform_keys! ⇒ Enumerator
self
#transform_keys!(other_hash) ⇒ self
#transform_keys!(other_hash) {|old_key| ... } ⇒ self
#transform_keys! ⇒ Enumerator
With an argument, a block, or both given, derives keys from the argument, the block, and self; all, some, or none of the keys in self may be changed.
With a block given and no argument, derives keys only from the block; all, some, or none of the keys in self may be changed.
For each key/value pair old_key/value in self, calls the block with old_key; the block’s return value becomes new_key; removes the entry for old_key: self.delete(old_key); sets self[new_key] = value; a duplicate key overwrites:
h = {foo: 0, bar: 1, baz: 2}
h.transform_keys! {|old_key| old_key.to_s }
# => {"foo" => 0, "bar" => 1, "baz" => 2}
h = {foo: 0, bar: 1, baz: 2}
h.transform_keys! {|old_key| 'xxx' }
# => {"xxx" => 2}
With argument other_hash given and no block, derives keys for self from other_hash and self; all, some, or none of the keys in self may be changed.
For each key/value pair old_key/old_value in self, looks for key old_key in other_hash:
-
If
old_keyis found, takes valueother_hash[old_key]asnew_key; removes the entry forold_key:self.delete(old_key); setsself[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :BAZ, bar: :BAR, foo: :FOO) # => {FOO: 0, BAR: 1, BAZ: 2} h = {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :FOO, bar: :FOO, foo: :FOO) # => {FOO: 2} -
If
old_keyis not found, does nothing:h = {foo: 0, bar: 1, baz: 2} h.transform_keys!({}) # => {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :foo) # => {foo: 2, bar: 1}
Unused keys in other_hash are ignored:
h = {foo: 0, bar: 1, baz: 2}
h.transform_keys!(bat: 3)
# => {foo: 0, bar: 1, baz: 2}
With both argument other_hash and a block given, derives keys from other_hash, the block, and self; all, some, or none of the keys in self may be changed.
For each pair old_key and value in self:
-
If
other_hashhas keyold_key(with valuenew_key), does not call the block for that key; removes the entry forold_key:self.delete(old_key); setsself[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :BAZ, bar: :BAR, foo: :FOO) {|key| fail 'Not called' } # => {FOO: 0, BAR: 1, BAZ: 2} -
If
other_hashdoes not have keyold_key, calls the block withold_keyand takes its return value asnew_key; removes the entry forold_key:self.delete(old_key); setsself[new_key] = value; a duplicate key overwrites:h = {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :BAZ) {|key| key.to_s.reverse } # => {"oof" => 0, "rab" => 1, BAZ: 2} h = {foo: 0, bar: 1, baz: 2} h.transform_keys!(baz: :BAZ) {|key| 'ook' } # => {"ook" => 1, BAZ: 2}
With no argument and no block given, returns a new ::Enumerator.
Related: see Methods for Transforming Keys and Values.
# File 'hash.c', line 3390
static VALUE
rb_hash_transform_keys_bang(int argc, VALUE *argv, VALUE hash)
{
VALUE trans = 0;
int block_given = 0;
argc = rb_check_arity(argc, 0, 1);
if (argc > 0) {
trans = to_hash(argv[0]);
block_given = rb_block_given_p();
}
else {
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
}
rb_hash_modify_check(hash);
if (!RHASH_TABLE_EMPTY_P(hash)) {
long i;
VALUE new_keys = hash_alloc(0);
VALUE pairs = rb_ary_hidden_new(RHASH_SIZE(hash) * 2);
rb_hash_foreach(hash, flatten_i, pairs);
for (i = 0; i < RARRAY_LEN(pairs); i += 2) {
VALUE key = RARRAY_AREF(pairs, i), new_key, val;
if (!trans) {
new_key = rb_yield(key);
}
else if (!UNDEF_P(new_key = rb_hash_lookup2(trans, key, Qundef))) {
/* use the transformed key */
}
else if (block_given) {
new_key = rb_yield(key);
}
else {
new_key = key;
}
val = RARRAY_AREF(pairs, i+1);
if (!hash_stlike_lookup(new_keys, key, NULL)) {
rb_hash_stlike_delete(hash, &key, NULL);
}
rb_hash_aset(hash, new_key, val);
rb_hash_aset(new_keys, new_key, Qnil);
}
rb_ary_clear(pairs);
rb_hash_clear(new_keys);
}
compact_after_delete(hash);
return hash;
}
#transform_values {|value| ... } ⇒ Hash
#transform_values ⇒ Enumerator
Hash
#transform_values ⇒ Enumerator
With a block given, returns a new hash new_hash; for each pair key+/+value in self, calls the block with value and captures its return as new_value; adds to new_hash the entry key+/+new_value:
h = {foo: 0, bar: 1, baz: 2}
h1 = h.transform_values {|value| value * 100}
h1 # => {foo: 0, bar: 100, baz: 200}
With no block given, returns a new ::Enumerator.
Related: see Methods for Transforming Keys and Values.
# File 'hash.c', line 3487
static VALUE
rb_hash_transform_values(VALUE hash)
{
VALUE result;
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
result = hash_dup_with_compare_by_id(hash);
SET_DEFAULT(result, Qnil);
if (!RHASH_EMPTY_P(hash)) {
transform_values(result);
compact_after_delete(result);
}
return result;
}
#transform_values! {|old_value| ... } ⇒ self
#transform_values! ⇒ Enumerator
self
#transform_values! ⇒ Enumerator
With a block given, changes the values of self as determined by the block; returns self.
For each entry key+/+old_value in self, calls the block with old_value, captures its return value as new_value, and sets self[key] = new_value:
h = {foo: 0, bar: 1, baz: 2}
h.transform_values! {|value| value * 100} # => {foo: 0, bar: 100, baz: 200}
With no block given, returns a new ::Enumerator.
Related: see Methods for Transforming Keys and Values.
# File 'hash.c', line 3525
static VALUE
rb_hash_transform_values_bang(VALUE hash)
{
RETURN_SIZED_ENUMERATOR(hash, 0, 0, hash_enum_size);
rb_hash_modify_check(hash);
if (!RHASH_TABLE_EMPTY_P(hash)) {
transform_values(hash);
}
return hash;
}
#update(*other_hashes) ⇒ self
#update(*other_hashes) {|key, old_value, new_value| ... } ⇒ self
self
#update(*other_hashes) {|key, old_value, new_value| ... } ⇒ self
Alias for #merge!.
#value?(value) ⇒ Boolean Also known as: #has_value?
Returns whether value is a value in self.
Related: Methods for Querying.
# File 'hash.c', line 3885
static VALUE
rb_hash_has_value(VALUE hash, VALUE val)
{
VALUE data[2];
data[0] = Qfalse;
data[1] = val;
rb_hash_foreach(hash, rb_hash_search_value, (VALUE)data);
return data[0];
}
#values ⇒ Array
Returns a new array containing all values in self:
h = {foo: 0, bar: 1, baz: 2}
h.values # => [0, 1, 2]
Related: see Methods for Fetching.
# File 'hash.c', line 3813
VALUE
rb_hash_values(VALUE hash)
{
VALUE values;
st_index_t size = RHASH_SIZE(hash);
values = rb_ary_new_capa(size);
if (size == 0) return values;
if (ST_DATA_COMPATIBLE_P(VALUE)) {
if (RHASH_AR_TABLE_P(hash)) {
rb_gc_writebarrier_remember(values);
RARRAY_PTR_USE(values, ptr, {
size = ar_values(hash, ptr, size);
});
}
else if (RHASH_ST_TABLE_P(hash)) {
st_table *table = RHASH_ST_TABLE(hash);
rb_gc_writebarrier_remember(values);
RARRAY_PTR_USE(values, ptr, {
size = st_values(table, ptr, size);
});
}
rb_ary_set_len(values, size);
}
else {
rb_hash_foreach(hash, values_i, values);
}
return values;
}
#values_at(*keys) ⇒ Array
Returns a new array containing values for the given #keys:
h = {foo: 0, bar: 1, baz: 2}
h.values_at(:baz, :foo) # => [2, 0]
The hash default is returned for each key that is not found:
h.values_at(:hello, :foo) # => [nil, 0]
Related: see Methods for Fetching.
# File 'hash.c', line 2685
static VALUE
rb_hash_values_at(int argc, VALUE *argv, VALUE hash)
{
VALUE result = rb_ary_new2(argc);
long i;
for (i=0; i<argc; i++) {
rb_ary_push(result, rb_hash_aref(hash, argv[i]));
}
return result;
}