arrayfields 3.7.0 → 4.0.0

Sign up to get free protection for your applications and to get access to all the features.
data/README CHANGED
@@ -2,11 +2,29 @@ NAME
2
2
  arrayfields.rb
3
3
 
4
4
  URIS
5
- http://rubyforge.org/projects/arrayfields/
6
- http://www.codeforpeople.com/lib/ruby/arrayfields/
7
- http://raa.ruby-lang.org/project/arrayfields/
5
+ http://www.codeforpeople.com/lib/ruby/
6
+ http://rubyforge.org/projects/codeforpeople/
8
7
 
9
8
  SYNOPSIS
9
+ require 'arrayfields'
10
+
11
+ a = Arrayfields.new :k, :v, :a, :b
12
+
13
+ p a[:k] #=> :v
14
+ p a[:a] #=> :b
15
+ p a.fields #=> [:k, :a]
16
+ p a.values #=> [:v, :b]
17
+ p a #=> [:v, :b]
18
+ p a.to_hash #=> {:k => :v, :a => :b}
19
+ p a.pairs #=> [[:k, :v], [:a, :b]]
20
+
21
+ a[:foo] = :bar
22
+
23
+ p a[:foo] #=> :bar
24
+ p a.fields #=> [:k, :a, :foo]
25
+
26
+ AND
27
+
10
28
  require 'arrayfields'
11
29
 
12
30
  fields = 'name', 'age'
@@ -14,18 +32,18 @@ SYNOPSIS
14
32
 
15
33
  a.fields = fields
16
34
 
17
- a[ 'name' ] #=> 'zaphod'
18
- a[ :name ] #=> 'zaphod'
19
- a.indices 'name', 'age' #=> [ 'zaphod', 42 ]
35
+ a['name'] #=> 'zaphod'
36
+ a[:name ] #=> 'zaphod'
37
+ a.indices 'name', 'age' #=> [ 'zaphod', 42 ]
20
38
 
21
39
  DESCRIPTION
22
40
  allow keyword access to array instances. arrayfields works by adding only a
23
- few methods to arrays, namely #fields= and fields, but the #fields= method
24
- is hooked to extend arrays on a per object basis. in otherwords __only__
25
- those arrays whose fields are set will have auto-magical keyword access
26
- bestowed on them - all other arrays remain unaffected. arrays with keyword
27
- access require much less memory when compared to hashes/objects and yet
28
- still provide fast lookup.
41
+ few methods to arrays, namely #fields= and fields, but the #fields= method is
42
+ hooked to extend an array on a per object basis. in otherwords __only__ those
43
+ arrays whose fields are set will have auto-magical keyword access bestowed on
44
+ them - all other arrays remain unaffected. arrays with keyword access require
45
+ much less memory when compared to hashes/objects and yet still provide fast
46
+ lookup and preserve data order.
29
47
 
30
48
  LIST OF OVERRIDDEN METHODS
31
49
  Array#[]
@@ -58,6 +76,7 @@ LIST OF HASH-LIKE METHODS
58
76
  Array#update
59
77
  Array#replace
60
78
  Array#invert
79
+ Array#pairs
61
80
 
62
81
  LIST OF ADDED Array METHODS
63
82
  Array#fields=
@@ -136,11 +155,11 @@ SAMPLES
136
155
 
137
156
  require 'arrayfields'
138
157
  #
139
- # the struct/fields factory method can be used in much the same way as ruby's
158
+ # the struct class factory method can be used in much the same way as ruby's
140
159
  # own struct generators and is useful when the fields for a set of arrays is
141
160
  # known apriori
142
161
  #
143
- c = Array.fields :a, :b, :c # same as Array.struct
162
+ c = Array.struct :a, :b, :c # class generator
144
163
  a = c.new [42, nil, nil]
145
164
  a[:c] = 42
146
165
  p a #=> [42, nil, 42]
@@ -158,13 +177,81 @@ SAMPLES
158
177
  [42, nil, 42, 42.0]
159
178
 
160
179
 
180
+ <========< sample/c.rb >========>
181
+
182
+ ~ > cat sample/c.rb
183
+
184
+ require 'arrayfields'
185
+ #
186
+ # the Array.fields methods generates an insance with those fields
187
+ #
188
+ a = Array.fields :a, :b, :c
189
+ a[:a] = a[:c] = 42
190
+ p a #=> [42, nil, 42]
191
+ p a.fields #=> [:a, :b, :c]
192
+ p a.values #=> [42, nil, 42]
193
+
194
+ ~ > ruby sample/c.rb
195
+
196
+ [42, nil, 42]
197
+ [:a, :b, :c]
198
+ [42, nil, 42]
199
+
200
+
201
+ <========< sample/d.rb >========>
202
+
203
+ ~ > cat sample/d.rb
204
+
205
+ require 'arrayfields'
206
+ #
207
+ # the Arrayfields.new method is a contruct that takes evenly numbered pairs of
208
+ # arbitrary objects and builds up and fielded array
209
+ #
210
+ a = Arrayfields.new :key, :value, :a, :b
211
+ p a.fields #=> [:key, :a]
212
+ p a.values #=> [:value, :b]
213
+ #
214
+ # you can use a hash - but of course the ordering gets lost in the initial
215
+ # hash creation. aka the order of fields get horked by the unorderedness if
216
+ # the hash iteration. it's okay for some purposed though
217
+ #
218
+ a = Arrayfields.new :key => :value, :a => :b
219
+ p a.fields #=> [:key, :a]
220
+ p a.values #=> [:value, :b]
221
+ #
222
+ # lists of pairs get flattened - the result simply has to be evenly numbered
223
+ #
224
+ a = Arrayfields.new [[:key, :value], [:a, :b]]
225
+ p a.fields #=> [:key, :a]
226
+ p a.values #=> [:value, :b]
227
+ p a.pairs #=> [[:key, :value], [:a, :b]]
228
+
229
+
230
+ ~ > ruby sample/d.rb
231
+
232
+ [:key, :a]
233
+ [:value, :b]
234
+ [:key, :a]
235
+ [:value, :b]
236
+ [:key, :a]
237
+ [:value, :b]
238
+ [[:key, :value], [:a, :b]]
239
+
240
+
161
241
  AUTHOR
162
242
  ara.t.howard@gmail.com
163
243
 
164
244
  HISTORY
245
+ 4.0.0:
246
+ - added Arrayfields.new(*arbitrary_evenly_numbered_list_of_objects)
247
+ - added #to_pairs and #pairs
248
+ - tried but failed to recall what happend for version 3.8
249
+ - changed Array.fields to == Arrayfields.new (used to alias Array.struct)
250
+ - added impl of Fieldable#dup that sets fields in dupped object
251
+
165
252
  3.7.0:
166
- - cleaned up multiton pattern in ArrayFields::FieldSet
167
- - mods for ruby 1.8.6
253
+ - multiton pattern clean up, thanks gavin kistner!
254
+ - mods for ruby 1.8.6 (alias bug in 1.8.6 i think)
168
255
  - added PseudoHash class
169
256
  - added Array.struct/fields class generator
170
257
 
@@ -2,11 +2,29 @@ NAME
2
2
  arrayfields.rb
3
3
 
4
4
  URIS
5
- http://rubyforge.org/projects/arrayfields/
6
- http://www.codeforpeople.com/lib/ruby/arrayfields/
7
- http://raa.ruby-lang.org/project/arrayfields/
5
+ http://www.codeforpeople.com/lib/ruby/
6
+ http://rubyforge.org/projects/codeforpeople/
8
7
 
9
8
  SYNOPSIS
9
+ require 'arrayfields'
10
+
11
+ a = Arrayfields.new :k, :v, :a, :b
12
+
13
+ p a[:k] #=> :v
14
+ p a[:a] #=> :b
15
+ p a.fields #=> [:k, :a]
16
+ p a.values #=> [:v, :b]
17
+ p a #=> [:v, :b]
18
+ p a.to_hash #=> {:k => :v, :a => :b}
19
+ p a.pairs #=> [[:k, :v], [:a, :b]]
20
+
21
+ a[:foo] = :bar
22
+
23
+ p a[:foo] #=> :bar
24
+ p a.fields #=> [:k, :a, :foo]
25
+
26
+ AND
27
+
10
28
  require 'arrayfields'
11
29
 
12
30
  fields = 'name', 'age'
@@ -14,18 +32,18 @@ SYNOPSIS
14
32
 
15
33
  a.fields = fields
16
34
 
17
- a[ 'name' ] #=> 'zaphod'
18
- a[ :name ] #=> 'zaphod'
19
- a.indices 'name', 'age' #=> [ 'zaphod', 42 ]
35
+ a['name'] #=> 'zaphod'
36
+ a[:name ] #=> 'zaphod'
37
+ a.indices 'name', 'age' #=> [ 'zaphod', 42 ]
20
38
 
21
39
  DESCRIPTION
22
40
  allow keyword access to array instances. arrayfields works by adding only a
23
- few methods to arrays, namely #fields= and fields, but the #fields= method
24
- is hooked to extend arrays on a per object basis. in otherwords __only__
25
- those arrays whose fields are set will have auto-magical keyword access
26
- bestowed on them - all other arrays remain unaffected. arrays with keyword
27
- access require much less memory when compared to hashes/objects and yet
28
- still provide fast lookup.
41
+ few methods to arrays, namely #fields= and fields, but the #fields= method is
42
+ hooked to extend an array on a per object basis. in otherwords __only__ those
43
+ arrays whose fields are set will have auto-magical keyword access bestowed on
44
+ them - all other arrays remain unaffected. arrays with keyword access require
45
+ much less memory when compared to hashes/objects and yet still provide fast
46
+ lookup and preserve data order.
29
47
 
30
48
  LIST OF OVERRIDDEN METHODS
31
49
  Array#[]
@@ -58,6 +76,7 @@ LIST OF HASH-LIKE METHODS
58
76
  Array#update
59
77
  Array#replace
60
78
  Array#invert
79
+ Array#pairs
61
80
 
62
81
  LIST OF ADDED Array METHODS
63
82
  Array#fields=
@@ -73,6 +92,13 @@ AUTHOR
73
92
  ara.t.howard@gmail.com
74
93
 
75
94
  HISTORY
95
+ 4.0.0:
96
+ - added Arrayfields.new(*arbitrary_evenly_numbered_list_of_objects)
97
+ - added #to_pairs and #pairs
98
+ - tried but failed to recall what happend for version 3.8
99
+ - changed Array.fields to == Arrayfields.new (used to alias Array.struct)
100
+ - added impl of Fieldable#dup that sets fields in dupped object
101
+
76
102
  3.7.0:
77
103
  - multiton pattern clean up, thanks gavin kistner!
78
104
  - mods for ruby 1.8.6 (alias bug in 1.8.6 i think)
@@ -5,7 +5,7 @@
5
5
  # Array#fields= is called
6
6
  #
7
7
  module ArrayFields
8
- VERSION = '3.7.0' unless defined? VERSION
8
+ self::VERSION = '4.0.0' unless defined? self::VERSION
9
9
  def self.version() VERSION end
10
10
  #
11
11
  # multiton cache of fields - wraps fields and fieldpos map to save memory
@@ -154,8 +154,8 @@
154
154
  def each_key
155
155
  @fieldset.each{|field| yield field}
156
156
  end
157
- def each_value(*args, &block)
158
- each(*args, &block)
157
+ def each_value *args, &block
158
+ each *args, &block
159
159
  end
160
160
  def fetch key
161
161
  self[key] or raise IndexError, 'key not found'
@@ -243,7 +243,30 @@
243
243
  def invert
244
244
  to_hash.invert
245
245
  end
246
+
247
+ def to_pairs
248
+ fields.zip values
249
+ end
250
+ alias_method 'pairs', 'to_pairs'
251
+ end
252
+ Arrayfields = ArrayFields
253
+
254
+ module Arrayfields
255
+ def self.new *pairs
256
+ pairs = pairs.map{|pair| Enumerable === pair ? pair.to_a : pair}.flatten
257
+ raise ArgumentError, "pairs must be evenly sized" unless(pairs.size % 2 == 0)
258
+ (( array = [] )).fields = []
259
+ 0.step(pairs.size - 2, 2) do |a|
260
+ b = a + 1
261
+ array[ pairs[a] ] = pairs[b]
262
+ end
263
+ array
264
+ end
265
+ def self.[] *pairs
266
+ new *pairs
267
+ end
246
268
  end
269
+ def Arrayfields(*a, &b) Arrayfields.new(*a, &b) end
247
270
  #
248
271
  # Fieldable encapsulates methods in common for classes which may have their
249
272
  # fields set and subsequently be auto-extended by ArrayFields
@@ -254,7 +277,7 @@
254
277
  # keyword access
255
278
  #
256
279
  def fields= fields
257
- extend ArrayFields unless defined? @fieldset
280
+ extend ArrayFields unless ArrayFields === self
258
281
 
259
282
  @fieldset =
260
283
  if ArrayFields::FieldSet === fields
@@ -273,6 +296,15 @@
273
296
  def fields
274
297
  @fieldset and @fieldset.fields
275
298
  end
299
+ #
300
+ # override so dup takes a copy of @fieldset
301
+ #
302
+ def dup
303
+ obj = super
304
+ #obj.instance_eval{ remove_instance_variable '@fieldset' }
305
+ obj.fields = fields
306
+ obj
307
+ end
276
308
  end
277
309
  #
278
310
  # Array instances are extened with two methods only: Fieldable#fields= and
@@ -284,7 +316,7 @@
284
316
  include Fieldable
285
317
 
286
318
  class << self
287
- def fields *fields
319
+ def struct *fields
288
320
  Class.new(self) do
289
321
  const_set :FIELDS, ArrayFields::FieldSet.new(fields.flatten)
290
322
  include ArrayFields
@@ -295,7 +327,10 @@
295
327
  end
296
328
  end
297
329
  end
298
- alias_method 'struct', 'fields'
330
+ def fields *fields, &block
331
+ (( array = new(&block) )).fields = fields.map{|x| Enumerable === x ? x.to_a : x}.flatten
332
+ array
333
+ end
299
334
  end
300
335
  end
301
336
  #
@@ -315,7 +350,7 @@
315
350
  def [](*pairs)
316
351
  pairs.flatten!
317
352
  raise ArgumentError, "argument must be key/val pairs" unless
318
- (pairs.size % 2 == 0 and pairs.size >= 2)
353
+ (pairs.size % 2 == 0)
319
354
  fields, elements = [], []
320
355
  while((f = pairs.shift) and (e = pairs.shift))
321
356
  fields << f and elements << e
@@ -340,6 +375,7 @@
340
375
  class_eval "def #{ meth }(*a,&b); @a.#{ meth }(*a,&b);end"
341
376
  end
342
377
  end
378
+ Fieldedarray = FieldedArray
343
379
 
344
380
  class PseudoHash < ::Array
345
381
  class << self
@@ -355,8 +391,8 @@
355
391
  end
356
392
  end
357
393
  def initialize keys = [], values = []
358
- self.replace values
359
394
  self.fields = keys
395
+ self.replace values
360
396
  end
361
397
  def to_yaml opts = {}
362
398
  YAML::quick_emit object_id, opts do |out|
@@ -366,3 +402,4 @@
366
402
  end
367
403
  end
368
404
  end
405
+ Pseudohash = PseudoHash
@@ -5,7 +5,7 @@
5
5
  # Array#fields= is called
6
6
  #
7
7
  module ArrayFields
8
- VERSION = '3.7.0' unless defined? VERSION
8
+ self::VERSION = '4.0.0' unless defined? self::VERSION
9
9
  def self.version() VERSION end
10
10
  #
11
11
  # multiton cache of fields - wraps fields and fieldpos map to save memory
@@ -154,8 +154,8 @@
154
154
  def each_key
155
155
  @fieldset.each{|field| yield field}
156
156
  end
157
- def each_value(*args, &block)
158
- each(*args, &block)
157
+ def each_value *args, &block
158
+ each *args, &block
159
159
  end
160
160
  def fetch key
161
161
  self[key] or raise IndexError, 'key not found'
@@ -243,7 +243,30 @@
243
243
  def invert
244
244
  to_hash.invert
245
245
  end
246
+
247
+ def to_pairs
248
+ fields.zip values
249
+ end
250
+ alias_method 'pairs', 'to_pairs'
251
+ end
252
+ Arrayfields = ArrayFields
253
+
254
+ module Arrayfields
255
+ def self.new *pairs
256
+ pairs = pairs.map{|pair| Enumerable === pair ? pair.to_a : pair}.flatten
257
+ raise ArgumentError, "pairs must be evenly sized" unless(pairs.size % 2 == 0)
258
+ (( array = [] )).fields = []
259
+ 0.step(pairs.size - 2, 2) do |a|
260
+ b = a + 1
261
+ array[ pairs[a] ] = pairs[b]
262
+ end
263
+ array
264
+ end
265
+ def self.[] *pairs
266
+ new *pairs
267
+ end
246
268
  end
269
+ def Arrayfields(*a, &b) Arrayfields.new(*a, &b) end
247
270
  #
248
271
  # Fieldable encapsulates methods in common for classes which may have their
249
272
  # fields set and subsequently be auto-extended by ArrayFields
@@ -254,7 +277,7 @@
254
277
  # keyword access
255
278
  #
256
279
  def fields= fields
257
- extend ArrayFields unless defined? @fieldset
280
+ extend ArrayFields unless ArrayFields === self
258
281
 
259
282
  @fieldset =
260
283
  if ArrayFields::FieldSet === fields
@@ -273,6 +296,15 @@
273
296
  def fields
274
297
  @fieldset and @fieldset.fields
275
298
  end
299
+ #
300
+ # override so dup takes a copy of @fieldset
301
+ #
302
+ def dup
303
+ obj = super
304
+ #obj.instance_eval{ remove_instance_variable '@fieldset' }
305
+ obj.fields = fields
306
+ obj
307
+ end
276
308
  end
277
309
  #
278
310
  # Array instances are extened with two methods only: Fieldable#fields= and
@@ -284,7 +316,7 @@
284
316
  include Fieldable
285
317
 
286
318
  class << self
287
- def fields *fields
319
+ def struct *fields
288
320
  Class.new(self) do
289
321
  const_set :FIELDS, ArrayFields::FieldSet.new(fields.flatten)
290
322
  include ArrayFields
@@ -295,7 +327,10 @@
295
327
  end
296
328
  end
297
329
  end
298
- alias_method 'struct', 'fields'
330
+ def fields *fields, &block
331
+ (( array = new(&block) )).fields = fields.map{|x| Enumerable === x ? x.to_a : x}.flatten
332
+ array
333
+ end
299
334
  end
300
335
  end
301
336
  #
@@ -315,7 +350,7 @@
315
350
  def [](*pairs)
316
351
  pairs.flatten!
317
352
  raise ArgumentError, "argument must be key/val pairs" unless
318
- (pairs.size % 2 == 0 and pairs.size >= 2)
353
+ (pairs.size % 2 == 0)
319
354
  fields, elements = [], []
320
355
  while((f = pairs.shift) and (e = pairs.shift))
321
356
  fields << f and elements << e
@@ -340,6 +375,7 @@
340
375
  class_eval "def #{ meth }(*a,&b); @a.#{ meth }(*a,&b);end"
341
376
  end
342
377
  end
378
+ Fieldedarray = FieldedArray
343
379
 
344
380
  class PseudoHash < ::Array
345
381
  class << self
@@ -355,8 +391,8 @@
355
391
  end
356
392
  end
357
393
  def initialize keys = [], values = []
358
- self.replace values
359
394
  self.fields = keys
395
+ self.replace values
360
396
  end
361
397
  def to_yaml opts = {}
362
398
  YAML::quick_emit object_id, opts do |out|
@@ -366,3 +402,4 @@
366
402
  end
367
403
  end
368
404
  end
405
+ Pseudohash = PseudoHash
@@ -1,10 +1,10 @@
1
1
  require 'arrayfields'
2
2
  #
3
- # the struct/fields factory method can be used in much the same way as ruby's
3
+ # the struct class factory method can be used in much the same way as ruby's
4
4
  # own struct generators and is useful when the fields for a set of arrays is
5
5
  # known apriori
6
6
  #
7
- c = Array.fields :a, :b, :c # same as Array.struct
7
+ c = Array.struct :a, :b, :c # class generator
8
8
  a = c.new [42, nil, nil]
9
9
  a[:c] = 42
10
10
  p a #=> [42, nil, 42]
@@ -0,0 +1,9 @@
1
+ require 'arrayfields'
2
+ #
3
+ # the Array.fields methods generates an insance with those fields
4
+ #
5
+ a = Array.fields :a, :b, :c
6
+ a[:a] = a[:c] = 42
7
+ p a #=> [42, nil, 42]
8
+ p a.fields #=> [:a, :b, :c]
9
+ p a.values #=> [42, nil, 42]
@@ -0,0 +1,24 @@
1
+ require 'arrayfields'
2
+ #
3
+ # the Arrayfields.new method is a contruct that takes evenly numbered pairs of
4
+ # arbitrary objects and builds up and fielded array
5
+ #
6
+ a = Arrayfields.new :key, :value, :a, :b
7
+ p a.fields #=> [:key, :a]
8
+ p a.values #=> [:value, :b]
9
+ #
10
+ # you can use a hash - but of course the ordering gets lost in the initial
11
+ # hash creation. aka the order of fields get horked by the unorderedness if
12
+ # the hash iteration. it's okay for some purposed though
13
+ #
14
+ a = Arrayfields.new :key => :value, :a => :b
15
+ p a.fields #=> [:key, :a]
16
+ p a.values #=> [:value, :b]
17
+ #
18
+ # lists of pairs get flattened - the result simply has to be evenly numbered
19
+ #
20
+ a = Arrayfields.new [[:key, :value], [:a, :b]]
21
+ p a.fields #=> [:key, :a]
22
+ p a.values #=> [:value, :b]
23
+ p a.pairs #=> [[:key, :value], [:a, :b]]
24
+
metadata CHANGED
@@ -3,8 +3,8 @@ rubygems_version: 0.9.2
3
3
  specification_version: 1
4
4
  name: arrayfields
5
5
  version: !ruby/object:Gem::Version
6
- version: 3.7.0
7
- date: 2007-04-03 00:00:00 -06:00
6
+ version: 4.0.0
7
+ date: 2007-09-13 00:00:00 -06:00
8
8
  summary: arrayfields
9
9
  require_paths:
10
10
  - lib
@@ -29,20 +29,22 @@ post_install_message:
29
29
  authors:
30
30
  - Ara T. Howard
31
31
  files:
32
- - install.rb
33
- - gen_readme.rb
34
32
  - gemspec.rb
35
- - README.tmpl
33
+ - gen_readme.rb
34
+ - install.rb
36
35
  - lib
36
+ - lib/arrayfields-4.0.0.rb
37
37
  - lib/arrayfields.rb
38
- - lib/arrayfields-3.7.0.rb
39
- - test
40
- - test/arrayfields.rb
41
- - test/memtest.rb
38
+ - README
39
+ - README.tmpl
42
40
  - sample
43
41
  - sample/a.rb
44
42
  - sample/b.rb
45
- - README
43
+ - sample/c.rb
44
+ - sample/d.rb
45
+ - test
46
+ - test/arrayfields.rb
47
+ - test/memtest.rb
46
48
  test_files:
47
49
  - test/arrayfields.rb
48
50
  rdoc_options: []