Class: Dictionary
Overview
Dictionary
The Dictionary class is a Hash that preserves order. So it has some array-like extensions also. By defualt a Dictionary object preserves insertion order, but any order can be specified including alphabetical key order.
Usage
Just require this file and use Dictionary instead of Hash.
hsh = Dictionary.new
hsh['z'] = 1
hsh['a'] = 2
hsh['c'] = 3
p hsh.keys
hsh = Dictionary['z', 1, 'a', 2, 'c', 3]
p hsh.keys
hsh = Dictionary['z'=>1, 'a'=>2, 'c'=>3]
p hsh.keys
p hsh.push('to_end', 15) p hsh.push('to_end', 30) p hsh.unshift('to_begin', 50) p hsh.unshift('to_begin', 60) p hsh.keys p hsh.pop p hsh.keys p hsh.shift
Usage Notes
-
You can use #order_by to set internal sort order.
-
#<< takes a two element [k,v] array and inserts.
-
Use ::auto which creates Dictionay sub-entries as needed.
-
And ::alpha which creates a new Dictionary sorted by key.
Class Method Summary
collapse
Instance Method Summary
collapse
-
#<<(kv) ⇒ Object
-
#==(hsh2) ⇒ Object
-
#[](k) ⇒ Object
-
#[]=(k, i = nil, v = nil) ⇒ Object
-
#clear ⇒ Object
-
#delete(key) ⇒ Object
-
#delete_if ⇒ Object
-
#dup ⇒ Object
-
#each ⇒ Object
(also: #each_pair)
-
#each_key ⇒ Object
-
#each_value ⇒ Object
-
#empty? ⇒ Boolean
-
#fetch(k, *a, &b) ⇒ Object
-
#first ⇒ Object
-
#has_key?(key) ⇒ Boolean
-
#initialize(*args, &blk) ⇒ Dictionary
constructor
-
#insert(i, k, v) ⇒ Object
-
#inspect ⇒ Object
-
#invert ⇒ Object
-
#key?(key) ⇒ Boolean
-
#keys ⇒ Object
-
#last ⇒ Object
-
#length ⇒ Object
(also: #size)
-
#merge(hsh2) ⇒ Object
-
#order ⇒ Object
-
#order_by(&block) ⇒ Object
Keep dictionary sorted by a specific sort order.
-
#order_by_key ⇒ Object
Keep dictionary sorted by key.
-
#order_by_value ⇒ Object
Keep dictionary sorted by value.
-
#pop ⇒ Object
-
#push(k, v) ⇒ Object
-
#reject(&block) ⇒ Object
-
#reject!(&block) ⇒ Object
-
#reorder ⇒ Object
-
#replace(hsh2) ⇒ Object
-
#reverse ⇒ Object
-
#reverse! ⇒ Object
-
#select ⇒ Object
-
#shift ⇒ Object
-
#store(a, b) ⇒ Object
-
#to_a ⇒ Object
-
#to_h ⇒ Object
-
#to_hash ⇒ Object
-
#to_json ⇒ Object
-
#to_s ⇒ Object
-
#unshift(k, v) ⇒ Object
-
#update(hsh2) ⇒ Object
(also: #merge!)
-
#values ⇒ Object
Methods included from Enumerable
#each_with_object, #group_by, #index_by, #many?, #sum
Constructor Details
#initialize(*args, &blk) ⇒ Dictionary
136
137
138
139
140
141
142
143
144
145
146
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 136
def initialize(*args, &blk)
@order = []
@order_by = nil
if blk
dict = self oblk = lambda{ |hsh, key| blk[dict,key] } @hash = Hash.new(*args, &oblk)
else
@hash = Hash.new(*args)
end
end
|
Class Method Details
.[](*args) ⇒ Object
– TODO is this needed? Doesn’t the super class do this? ++
88
89
90
91
92
93
94
95
96
97
98
99
100
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 88
def [](*args)
hsh = new
if Hash === args[0]
hsh.replace(args[0])
elsif (args.size % 2) != 0
raise ArgumentError, "odd number of elements for Hash"
else
while !args.empty?
hsh[args.shift] = args.shift
end
end
hsh
end
|
.alpha(*args, &block) ⇒ Object
Alternate to #new which creates a dictionary sorted by key.
d = Dictionary.alpha
d["z"] = 1
d["y"] = 2
d["x"] = 3
d
This is equivalent to:
Dictionary.new.order_by { |key,value| key }
119
120
121
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 119
def alpha(*args, &block)
new(*args, &block).order_by_key
end
|
.auto(*args) ⇒ Object
Alternate to #new which auto-creates sub-dictionaries as needed.
d = Dictionary.auto
d["a"]["b"]["c"] = "abc"
128
129
130
131
132
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 128
def auto(*args)
leet = lambda { |hsh, key| hsh[key] = new(&leet) }
new(*args, &leet)
end
|
.new_by(*args, &blk) ⇒ Object
Like #new but the block sets the order.
104
105
106
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 104
def new_by(*args, &blk)
new(*args).order_by(&blk)
end
|
Instance Method Details
323
324
325
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 323
def <<(kv)
push( *kv )
end
|
205
206
207
208
209
210
211
212
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 205
def ==(hsh2)
if hsh2.is_a?( Dictionary )
@order == hsh2.order &&
@hash == hsh2.instance_variable_get("@hash")
else
false
end
end
|
214
215
216
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 214
def [] k
@hash[ k ]
end
|
#[]=(k, i = nil, v = nil) ⇒ Object
Store operator.
h[key] = value
Or with additional index.
h[key,index] = value
229
230
231
232
233
234
235
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 229
def []=(k, i=nil, v=nil)
if v
insert(i,k,v)
else
store(k,i)
end
end
|
247
248
249
250
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 247
def clear
@order = []
@hash.clear
end
|
#delete(key) ⇒ Object
252
253
254
255
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 252
def delete( key )
@order.delete( key )
@hash.delete( key )
end
|
#delete_if ⇒ Object
273
274
275
276
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 273
def delete_if
order.clone.each { |k| delete k if yield(k,@hash[k]) }
self
end
|
348
349
350
351
352
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 348
def dup
a = []
each{ |k,v| a << k; a << v }
self.class[*a]
end
|
#each ⇒ Object
Also known as:
each_pair
267
268
269
270
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 267
def each
order.each { |k| yield( k,@hash[k] ) }
self
end
|
257
258
259
260
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 257
def each_key
order.each { |k| yield( k ) }
self
end
|
#each_value ⇒ Object
262
263
264
265
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 262
def each_value
order.each { |k| yield( @hash[k] ) }
self
end
|
#empty? ⇒ Boolean
393
394
395
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 393
def empty?
@hash.empty?
end
|
#fetch(k, *a, &b) ⇒ Object
218
219
220
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 218
def fetch(k, *a, &b)
@hash.fetch(k, *a, &b)
end
|
380
381
382
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 380
def first
@hash[order.first]
end
|
#has_key?(key) ⇒ Boolean
397
398
399
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 397
def has_key?(key)
@hash.has_key?(key)
end
|
#insert(i, k, v) ⇒ Object
237
238
239
240
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 237
def insert( i,k,v )
@order.insert( i,k )
@hash.store( k,v )
end
|
342
343
344
345
346
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 342
def inspect
ary = []
each {|k,v| ary << k.inspect + "=>" + v.inspect}
'{' + ary.join(", ") + '}'
end
|
288
289
290
291
292
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 288
def invert
hsh2 = self.class.new
order.each { |k| hsh2[@hash[k]] = k }
hsh2
end
|
#key?(key) ⇒ Boolean
401
402
403
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 401
def key?(key)
@hash.key?(key)
end
|
284
285
286
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 284
def keys
order
end
|
384
385
386
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 384
def last
@hash[order.last]
end
|
#length ⇒ Object
Also known as:
size
388
389
390
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 388
def length
@order.length
end
|
#merge(hsh2) ⇒ Object
361
362
363
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 361
def merge( hsh2 )
self.dup.update(hsh2)
end
|
148
149
150
151
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 148
def order
reorder if @order_by
@order
end
|
#order_by(&block) ⇒ Object
Keep dictionary sorted by a specific sort order.
154
155
156
157
158
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 154
def order_by( &block )
@order_by = block
order
self
end
|
#order_by_key ⇒ Object
Keep dictionary sorted by key.
d = Dictionary.new.order_by_key
d["z"] = 1
d["y"] = 2
d["x"] = 3
d
This is equivalent to:
Dictionary.new.order_by { |key,value| key }
The initializer Dictionary#alpha also provides this.
173
174
175
176
177
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 173
def order_by_key
@order_by = lambda { |k,v| k }
order
self
end
|
#order_by_value ⇒ Object
Keep dictionary sorted by value.
d = Dictionary.new.order_by_value
d["z"] = 1
d["y"] = 2
d["x"] = 3
d
This is equivalent to:
Dictionary.new.order_by { |key,value| value }
190
191
192
193
194
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 190
def order_by_value
@order_by = lambda { |k,v| v }
order
self
end
|
337
338
339
340
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 337
def pop
key = order.last
key ? [key,delete(key)] : nil
end
|
#push(k, v) ⇒ Object
327
328
329
330
331
332
333
334
335
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 327
def push( k,v )
unless @hash.include?( k )
@order.push( k )
@hash.store( k,v )
true
else
false
end
end
|
#reject(&block) ⇒ Object
294
295
296
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 294
def reject( &block )
self.dup.delete_if(&block)
end
|
#reject!(&block) ⇒ Object
298
299
300
301
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 298
def reject!( &block )
hsh2 = reject(&block)
self == hsh2 ? nil : hsh2
end
|
197
198
199
200
201
202
203
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 197
def reorder
if @order_by
assoc = @order.collect{ |k| [k,@hash[k]] }.sort_by(&@order_by)
@order = assoc.collect{ |k,v| k }
end
@order
end
|
#replace(hsh2) ⇒ Object
303
304
305
306
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 303
def replace( hsh2 )
@order = hsh2.order
@hash = hsh2.hash
end
|
376
377
378
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 376
def reverse
dup.reverse!
end
|
371
372
373
374
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 371
def reverse!
@order.reverse!
self
end
|
365
366
367
368
369
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 365
def select
ary = []
each { |k,v| ary << [k,v] if yield k,v }
ary
end
|
308
309
310
311
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 308
def shift
key = order.first
key ? [key,delete(key)] : super
end
|
#store(a, b) ⇒ Object
242
243
244
245
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 242
def store( a,b )
@order.push( a ) unless @hash.has_key?( a )
@hash.store( a,b )
end
|
405
406
407
408
409
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 405
def to_a
ary = []
each { |k,v| ary << [k,v] }
ary
end
|
430
431
432
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 430
def to_h
@hash.dup
end
|
426
427
428
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 426
def to_hash
@hash.dup
end
|
411
412
413
414
415
416
417
418
419
420
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 411
def to_json
buf = "["
map do |k,v|
buf << k.to_json
buf << ", "
buf << v.to_json
end.join(", ")
buf << "]"
buf
end
|
422
423
424
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 422
def to_s
self.to_a.to_s
end
|
#unshift(k, v) ⇒ Object
313
314
315
316
317
318
319
320
321
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 313
def unshift( k,v )
unless @hash.include?( k )
@order.unshift( k )
@hash.store( k,v )
true
else
false
end
end
|
#update(hsh2) ⇒ Object
Also known as:
merge!
354
355
356
357
358
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 354
def update( hsh2 )
hsh2.each { |k,v| self[k] = v }
reorder
self
end
|
278
279
280
281
282
|
# File 'lib/gems/extlib-0.9.9/lib/extlib/dictionary.rb', line 278
def values
ary = []
order.each { |k| ary.push @hash[k] }
ary
end
|