rbbt-util 5.0.1 → 5.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/README.rdoc CHANGED
@@ -12,7 +12,7 @@
12
12
  cp .bash_profile .bash_profile.save
13
13
  mv tmp.bash_profile .bash_profile
14
14
  . .bash_profile
15
- rvm install 1.8.7
15
+ rvm install 1.9.3
16
16
 
17
17
  2 - install tokyocabinet (Intructions for user install follow. For system level, make sure we have dev package)
18
18
  1 - download source from http://fallabs.com/tokyocabinet/tokyocabinet-1.4.47.tar.gz
@@ -43,7 +43,7 @@
43
43
 
44
44
  :script
45
45
 
46
- gem install specific_install
46
+ gem install specific_install hoe
47
47
  gem specific_install -l https://github.com/bensomers/png.git
48
48
  gem specific_install -l https://github.com/felipec/soap4r.git
49
49
  gem specific_install -l https://github.com/mikisvaz/tokyocabinet_19_fix.git
@@ -53,18 +53,22 @@
53
53
  :script
54
54
 
55
55
  # RSRuby
56
- R_HOME='full_path_to_R_dir' # Example in ubuntu
56
+ ## Example in ubuntu
57
57
  gem install rsruby -- --with-R-dir=/usr/lib/R/lib/ --with-R-include=/usr/share/R/include
58
+
59
+ ## Example in MAC
60
+ gem install rsruby -- --with-R-dir=/Library/Frameworks/R.framework/Resources/
61
+
58
62
 
59
63
  # JRB
60
64
  export JAVA_HOME="full_path_to_jdk"
61
65
  gem install rjb
62
66
 
63
- 3 - install gems rbbt-util rbbt-sources rbbt-text rbbt-phgx.
67
+ 3 - install gems rbbt-util rbbt-sources rbbt-text rbbt-phgx, ...
64
68
 
65
69
  :script
66
70
 
67
- gem install rbbt-util rbbt-sources rbbt-text rbbt-phgx rbbt-entities rbbt-views
71
+ gem install rbbt-util rbbt-sources rbbt-text rbbt-phgx rbbt-entities rbbt-views rbbt-dm rbbt-GE
68
72
 
69
73
  3.bis - Or install github repos and make ruby use them
70
74
 
@@ -82,13 +86,19 @@
82
86
  alias druby="env RBBT_LOG=0 ruby $(for d in $HOME/git/rbbt-*;do echo -n "-I$d/lib ";done)"
83
87
  alias drake="env RBBT_LOG=0 rake $(for d in $HOME/git/rbbt-*;do echo -n "-I$d/lib ";done)"
84
88
 
85
- 4 - Set up R to find the helper lib
89
+ 4 - Install other gems that you might need for some of my workflows
90
+
91
+ script
92
+
93
+ gem install redcarpet thin
94
+
95
+ 5 - Set up R to find the helper lib
86
96
 
87
97
  :script
88
98
 
89
99
  echo "source(system('rbbt_Rutil.rb', intern =T));" >> $HOME/.Rprofile
90
100
 
91
- 5 - If you plan to run workflows you might want to redefine the default directory to place your workflows (~/.workflows)
101
+ 6 - If you plan to run workflows you might want to redefine the default directory to place your workflows (~/.workflows)
92
102
 
93
103
  :script
94
104
 
@@ -1,598 +1,300 @@
1
1
  require 'rbbt/util/misc'
2
- require 'rbbt/util/chain_methods'
2
+ require 'rbbt/annotations/annotated_array'
3
+ require 'rbbt/annotations/util'
3
4
 
4
- require 'json'
5
- module Annotated
6
- attr_accessor :annotation_types
7
- attr_accessor :context
8
- attr_accessor :container
9
- attr_accessor :container_index
10
- attr_accessor :id
11
-
12
- def self.extended(base)
13
- base.annotation_types ||= []
14
- end
5
+ #{{{ ANNOTATED
15
6
 
16
- def annotations
17
- raise "Annotation types is nil for object: #{self.inspect}" if annotation_types.nil?
18
- annotation_types.collect do |mod|
19
- mod.annotations
20
- end.flatten.uniq
21
- end
7
+ module Annotated
8
+ attr_accessor :container, :container_index
22
9
 
23
- def unmasked_annotations
24
- raise "Annotation types is nil for object: #{self.inspect}" if annotation_types.nil?
25
- annotation_types.collect do |mod|
26
- mod.unmasked_annotations
27
- end.flatten.uniq
10
+ def annotation_values
11
+ @annotation_values ||= {}
28
12
  end
29
13
 
30
- def info(masked = false)
31
- hash = {:annotation_types => annotation_types}
32
- (masked ? unmasked_annotations : annotations).each do |annotation|
33
- value = self.send(annotation)
34
- hash[annotation] = value unless value.nil?
35
- end
36
- hash
14
+ def detach_annotations
15
+ @annotation_values = @annotation_values.dup
16
+ @annotation_values.instance_variable_set(:@annotation_md5, nil)
17
+ @shared_annotations = false
37
18
  end
38
19
 
39
- def id
40
- @id ||= self.respond_to?(:annotation_id) ? annotation_id : Misc.hash2md5(info.merge(:self => self))
20
+ def reset
21
+ @info = nil
22
+ @id = nil
23
+ @self_md5 = nil
24
+ @annotation_values.instance_variable_set(:@annotation_md5, nil)
41
25
  end
42
26
 
43
- def self.load(object, info)
44
- annotation_types = info[:annotation_types] || []
45
- annotation_types = annotation_types.split("|") if String === annotation_types
46
-
47
- return object if annotation_types.nil? or annotation_types.empty?
27
+ def annotation_types
48
28
 
49
- annotated_array = info.delete(:annotated_array) || false
50
-
51
- annotation_types.each do |mod|
52
- mod = Misc.string2const(mod) if String === mod
53
- mod.setup(object, *info.values_at(*mod.all_annotations))
54
- end
55
-
56
- object.id = info[:entity_id] if info.include? :entity_id
57
-
58
- object.extend AnnotatedArray if annotated_array
59
-
60
- object
29
+ @annotation_types ||= class << self; self; end.
30
+ included_modules.
31
+ select{|m|
32
+ Annotation === m
33
+ }
61
34
  end
62
35
 
63
- def tsv_values(*fields)
64
- if Array === self and (not AnnotatedArray === self or self.double_array)
65
- Misc.zip_fields(self.compact.collect{|e| e.tsv_values(fields)})
66
- else
67
- fields = fields.flatten
68
- info = self.info
69
- info[:annotated_array] = true if AnnotatedArray === self
70
- values = []
71
-
72
- fields.each do |field|
73
- values << case
74
- when Proc === field
75
- field.call(self)
76
- when field == "JSON"
77
- info.to_json
78
- when field == "annotation_types"
79
- annotation_types.collect{|t| t.to_s} * "|"
80
- when field == "literal"
81
- (Array === self ? "Array:" << self * "|" : self).gsub(/\n|\t/, ' ')
82
- when info.include?(field.to_sym)
83
- res = info.delete(field.to_sym)
84
- Array === res ? "Array:" << res * "|" : res
85
- when self.respond_to?(field)
86
- res = self.send(field)
87
- Array === res ? "Array:"<< res * "|" : res
88
- end
89
- end
36
+ def annotations
37
+ if @annotations.nil?
38
+ @annotations = []
90
39
 
91
- values
92
- end
93
- end
40
+ annotation_types.each do |annotation_type|
41
+ @annotations.concat annotation_type.annotations
42
+ end
94
43
 
95
- def self.resolve_array(entry)
96
- if entry =~ /^Array:/
97
- entry["Array:".length..-1].split("|")
44
+ @annotations
98
45
  else
99
- entry
46
+ @annotations
100
47
  end
101
48
  end
102
49
 
103
- def self.load_tsv_values(id, values, *fields)
104
- fields = fields.flatten
105
- info = {}
106
- literal_pos = fields.index "literal"
107
-
108
- object = case
109
- when literal_pos
110
- values[literal_pos]
111
- else
112
- id.dup
113
- end
114
-
115
- object = resolve_array(object)
116
-
117
- if Array === values.first
118
- Misc.zip_fields(values).collect do |list|
119
- fields.each_with_index do |field,i|
120
- if field == "JSON"
121
- JSON.parse(list[i]).each do |key, value|
122
- info[key.to_sym] = value
123
- end
124
- else
125
- info[field.to_sym] = resolve_array(list[i])
126
- end
127
- end
50
+ def masked_annotations
51
+ if @masked_annotations.nil?
52
+ @masked_annotations = []
53
+
54
+ annotation_types.each do |annotation_type|
55
+ @masked_annotations.concat annotation_type.masked_annotations
128
56
  end
57
+
58
+ @masked_annotations
129
59
  else
130
- fields.each_with_index do |field,i|
131
- if field == "JSON"
132
- JSON.parse(values[i]).each do |key, value|
133
- info[key.to_sym] = value
134
- end
135
- else
136
- info[field.to_sym] = resolve_array(values[i])
137
- end
138
- end
60
+ @masked_annotations
139
61
  end
140
-
141
- self.load(object, info)
142
62
  end
143
63
 
144
- def self.json(annotations, literal = false)
145
- annotations = [annotations] unless Array === annotations
146
- hash = {}
147
- annotations.each do |annotation|
148
- if literal
149
- hash[annotation.id] = annotation.info.merge(:literal => annotation)
150
- else
151
- hash[annotation.id] = annotation.info
152
- end
153
- end
154
- hash.to_json
64
+ def unmasked_annotations
65
+ @unmasked_annotations ||= annotations - masked_annotations
155
66
  end
156
67
 
157
- def self.tsv(annotations, *fields)
158
- return nil if annotations.nil?
159
- fields = case
160
- when ((fields.compact.empty?) and not annotations.empty?)
161
- fields = AnnotatedArray === annotations ? annotations.annotations : annotations.compact.first.annotations
162
- fields << :annotation_types
163
- when (fields == [:literal] and not annotations.empty?)
164
- fields << :literal
165
- when (fields == [:all] and Annotated === annotations)
166
- fields = [:annotation_types] + annotations.annotations
167
- fields << :literal
168
- when (fields == [:all] and not annotations.empty?)
169
- raise "Input array must be annotated or its elements must be" if not Annotated === annotations.compact.first and not Array === annotations.compact.first
170
- raise "Input array must be annotated or its elements must be. No duble arrays of singly annotated entities." if not Annotated === annotations.compact.first and Array === annotations.compact.first
171
- fields = [:annotation_types] + (Annotated === annotations ?
172
- annotations.annotations :
173
- annotations.compact.first.annotations)
174
- fields << :literal
175
- when annotations.empty?
176
- [:annotation_types, :literal]
177
- else
178
- fields.flatten
179
- end
180
-
181
- fields = fields.collect{|f| f.to_s}
68
+ def info(masked = false)
182
69
 
183
- case
184
- when (Annotated === annotations and not (AnnotatedArray === annotations and annotations.double_array))
185
- tsv = TSV.setup({}, :key_field => "List", :fields => fields, :type => :list, :unnamed => true)
186
- annot_id = annotations.id
187
- tsv[annot_id] = annotations.tsv_values(*fields)
188
- when Array === annotations
189
- tsv = TSV.setup({}, :key_field => "ID", :fields => fields, :type => :list, :unnamed => true)
190
- annotations.compact.each_with_index do |annotation,i|
191
- tsv[annotation.id + ":" << i.to_s] = annotation.tsv_values(*fields)
192
- #tsv[annotation.id] = annotation.tsv_values(*fields)
193
- end
194
- else
195
- raise "Annotations need to be an Array to create TSV"
70
+ if @info.nil?
71
+ info = annotation_values.dup
72
+ info[:annotation_types] = annotation_types
73
+ info[:annotated_array] = true if AnnotatedArray === self
74
+ @info = info
196
75
  end
197
76
 
198
- tsv
199
- end
200
-
201
- def self.load_tsv(tsv)
202
- tsv.with_unnamed do
203
- annotated_entities = tsv.collect do |id, values|
204
- Annotated.load_tsv_values(id, values, tsv.fields)
205
- end
206
-
207
- case tsv.key_field
208
- when "List"
209
- annotated_entities.first
210
- else
211
- annotated_entities
77
+ if masked
78
+ if @masked_info.nil?
79
+ @masked_info = @info.dup
80
+ masked_annotations.each do |annotation|
81
+ @masked_info.delete annotation
82
+ end
212
83
  end
84
+ @masked_info
85
+ else
86
+ @info
213
87
  end
214
88
  end
215
89
 
216
- def make_list
217
- new = [self]
218
- annotation_types.each do |mod|
219
- mod.setup(new, *info.values_at(*mod.all_annotations))
90
+ def annotation_md5
91
+ if annotation_values.instance_variable_get(:@annotation_md5).nil?
92
+ annotation_values.instance_variable_set(:@annotation_md5, Misc.hash2md5(annotation_values))
220
93
  end
221
- new.context = self.context
222
- new
94
+ annotation_values.instance_variable_get(:@annotation_md5)
223
95
  end
224
96
 
225
- def annotate(object)
226
- annotation_types.each do |mod|
227
- mod.setup(object, *info.values_at(*mod.annotations))
228
- end
229
- object.context = self.context
230
- object.container = self.container
231
- object
97
+ def self_md5
98
+ @self_md5 ||= Misc.digest(annotation_md5 + self.to_s)
232
99
  end
233
- end
234
-
235
-
236
- module Annotation
237
- def self.extended(base)
238
- if not base.respond_to? :annotations
239
- class << base
240
- attr_accessor :annotations, :inheritance, :all_inheritance, :all_annotations, :masked_annotations
241
-
242
- def unmasked_annotations
243
- annotations - masked_annotations
244
- end
245
- self
246
- end
247
-
248
- base.annotations = []
249
- base.masked_annotations = []
250
- base.inheritance = []
251
- base.all_annotations = []
252
- base.all_inheritance = []
253
100
 
254
- base.module_eval do
255
- class << self
256
- alias prev_annotation_extended extended
257
- end
258
-
259
- def self.extended(object)
260
- self.send(:prev_annotation_extended, object)
261
- object.extend Annotated unless Annotated === object
262
- if not object.annotation_types.include? self
263
- object.annotation_types.concat self.inheritance
264
- object.annotation_types << self
265
- object.annotation_types.uniq!
266
- end
267
- end
101
+ # ToDo This does not make much sense, why not change :id directly
102
+ def id
103
+ @id ||= self.respond_to?(:annotation_id) ?
104
+ annotation_id : self_md5
105
+ end
268
106
 
269
- def self.included(base)
270
- base.inheritance << self
271
- base.all_inheritance.concat self.all_inheritance if self.respond_to? :all_inheritance
272
- base.all_inheritance << self
273
- base.all_inheritance.uniq!
274
- base.update_annotations
275
- end
276
- end
107
+ def annotate(object)
277
108
 
109
+ annotation_types.each do |annotation|
110
+ object.extend annotation
278
111
  end
279
- end
280
112
 
281
- def update_annotations
282
- @all_annotations = all_inheritance.inject([]){|acc,mod| acc.concat mod.all_annotations}.concat(@annotations)
283
- end
113
+ object.instance_variable_set(:@annotation_types, nil)
284
114
 
285
- def annotation(*values)
286
- @annotations.concat values.collect{|v| v.to_sym}
287
- update_annotations
115
+ if object.instance_variables.include?(:@annotation_values)
116
+ hash = {}
117
+ object.instance_variable_get(:@annotation_values).each{|k,v| hash[k] = v}
118
+ self.annotation_values.each{|k,v| hash[k] = v}
288
119
 
289
- module_eval do
290
- attr_accessor *values
120
+ object.instance_variable_set(:@annotation_values, hash)
121
+ object.instance_variable_set(:@shared_annotations, false)
122
+ else
123
+ object.instance_variable_set(:@annotation_values, self.annotation_values)
124
+ object.instance_variable_set(:@shared_annotations, true)
125
+ @shared_annotations = true
291
126
  end
292
- end
293
127
 
294
- def setup_info(object, info)
295
- object.extend self unless self === object
296
- all_annotations.each do |annotation|
297
- object.send(annotation.to_s + '=', info[annotation])
298
- end
128
+ object
299
129
  end
300
130
 
301
- def setup(object, *values)
302
- return nil if object.nil?
303
-
304
- object.extend self unless self === object
305
-
306
- if Hash === values.last
307
- values.last.each do |name, value|
308
- setter = "#{name}="
309
- next unless object.respond_to? setter
310
- value = value.split("|") if String === value and value.index "|"
311
- object.send("#{name}=", value)
131
+ def clean_annotations(recursive = false)
132
+ case
133
+ when self.nil?
134
+ nil
135
+ when Array === self
136
+ if recursive
137
+ [].concat self.collect{|e| e.respond_to?(:clean_annotations)? e.clean_annotations : e}
138
+ else
139
+ [].concat self
312
140
  end
141
+ when String === self
142
+ "" << self
313
143
  else
314
- all_annotations.zip(values).each do |name, value|
315
- value = value.split("|") if String === value and value.index "|"
316
- object.send("#{name}=", value)
317
- end
144
+ self.dup
318
145
  end
146
+ end
319
147
 
320
- object
148
+ def make_list
149
+ new = [self]
150
+ self.annotate(new)
151
+ new.extend AnnotatedArray
152
+ new
321
153
  end
322
154
  end
323
155
 
324
- module AnnotatedArray
325
- extend ChainMethods
326
156
 
327
- self.chain_prefix = :annotated_array
157
+ #{{{ ANNOTATION
328
158
 
329
- def double_array
330
- AnnotatedArray === self.send(:[], 0, true)
331
- end
159
+ module Annotation
160
+ attr_accessor :annotations, :masked_annotations
332
161
 
333
- def first
334
- self[0]
162
+ def annotations
163
+ @annotations ||= []
335
164
  end
336
165
 
337
- def last
338
- self[-1]
166
+ def masked_annotations
167
+ @masked_annotations ||= []
339
168
  end
340
169
 
341
- def [](pos, clean = false)
342
- value = super(pos)
343
- return nil if value.nil?
344
- return value if clean
345
- return value unless String === value or Array === value
346
-
347
- value = value.dup if value.frozen?
348
-
349
- annotation_types.each do |mod|
350
- value.extend mod unless mod === value
351
- mod.annotations.each do |annotation| value.send(annotation.to_s << "=", self.send(annotation)) end
352
- end
353
-
354
- value.context = self.context
355
- value.container = self
356
- value.container_index = pos
357
-
358
- value.extend AnnotatedArray if Array === value and AnnotatedArray === self
359
-
360
- value
170
+ def unmasked_annotations
171
+ annotations - masked_annotations
361
172
  end
362
173
 
363
- def each
364
- i = 0
365
- info = info
366
- super do |value|
367
- if String === value or Array === value
368
- value = value.dup if value.frozen? and not value.nil?
174
+ def annotation(*list)
369
175
 
370
- annotation_types.each do |mod|
371
- value.extend mod unless mod === value
372
- mod.annotations.each do |annotation| value.send(annotation.to_s << "=", self.send(annotation)) end
373
- end
374
-
375
- value.extend AnnotatedArray if Array === value and AnnotatedArray === self
376
-
377
- value.context = self.context
378
- value.container = self
379
- value.container_index = i
176
+ list.each do |annot|
177
+ next if annotations.include? annot.to_sym
178
+ annotations << annot.to_sym
380
179
 
180
+ # Getter
181
+ self.send(:define_method, annot.to_s) do
182
+ annotation_values[annot]
381
183
  end
382
184
 
383
- i += 1
384
-
385
- yield value
386
- end
387
- end
185
+ # Setter
186
+ self.send(:define_method, "#{ annot}=") do |value|
187
+ if @shared_annotations
188
+ detach_annotations # avoid side effects
189
+ end
388
190
 
389
- def collect
390
- res = []
191
+ reset
391
192
 
392
- if block_given?
393
- each do |value|
394
- res << yield(value)
395
- end
396
- else
397
- each do |value|
398
- res << value
193
+ annotation_values[annot] = value
399
194
  end
400
195
  end
401
-
402
- res
403
196
  end
404
197
 
405
- def select(method = nil, *args)
406
- res = []
407
- if method
408
- res = self.zip(self.send(method, *args)).select{|e,result| result}.collect{|element,r| element}
409
- else
410
- each do |value|
411
- res << value if yield(value)
412
- end
413
- end
414
-
415
- annotation_types.each do |mod|
416
- res.extend mod unless mod === res
417
- mod.annotations.each do |annotation| res.send(annotation.to_s + "=", self.send(annotation)) end
418
- end
419
-
420
- res.context = self.context
421
- res.container = self.container
422
-
423
- res.extend AnnotatedArray if AnnotatedArray === self
424
-
425
- res
198
+ def setup_hash(object, values)
199
+ object.instance_variable_set(:@annotation_values, values)
200
+ object.instance_variable_set(:@shared_annotations, true)
201
+ object.reset
202
+ object
426
203
  end
427
204
 
428
- def reject
429
- res = []
430
- each do |value|
431
- res << value unless yield(value)
432
- end
205
+ def clean_and_setup_hash(object, hash)
206
+ annotation_values = object.instance_variable_get(:@annotation_values)
207
+ annotation_values = annotation_values.nil? ? {} : annotation_values.dup
208
+ annotation_values.instance_variable_set(:@annotation_md5, nil)
433
209
 
434
- annotation_types.each do |mod|
435
- res.extend mod unless mod === res
436
- mod.annotations.each do |annotation| res.send(annotation.to_s + "=", self.send(annotation)) end
437
- end
438
-
439
- res.context = self.context
440
- res.container = self.container
441
-
442
- res.extend AnnotatedArray if AnnotatedArray === self
443
-
444
- res
445
- end
210
+ hash.each do |key, value|
211
+ begin
212
+ next unless @annotations.include? (key = key.to_sym)
213
+ rescue
214
+ next
215
+ end
446
216
 
447
- def subset(list)
448
- value = (self & list)
217
+ value = value.split("|") if String === value and value.index "|"
449
218
 
450
- annotation_types.each do |mod|
451
- value.extend mod unless mod === value
452
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
219
+ annotation_values[key] = value
453
220
  end
454
221
 
455
- value.context = self.context
456
- value.container = self.container
222
+ object.instance_variable_set(:@annotation_values, annotation_values)
223
+ object.instance_variable_set(:@shared_annotations, false)
457
224
 
458
- value.extend AnnotatedArray if AnnotatedArray === self
225
+ object.reset
459
226
 
460
- value
227
+ object
461
228
  end
462
229
 
463
- def remove(list)
464
- value = (self - list)
465
-
466
- annotation_types.each do |mod|
467
- value.extend mod unless mod === value
468
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
469
- end
470
-
471
- value.context = self.context
472
- value.container = self.container
230
+ def setup_positional(object, *values)
231
+ annotation_values = object.instance_variable_get(:@annotation_values)
232
+ annotation_values = annotation_values.nil? ? {} : annotation_values.dup
233
+ annotation_values.instance_variable_set(:@annotation_md5, nil)
473
234
 
474
- value.extend AnnotatedArray if AnnotatedArray === self
235
+ annotations.zip(values).each do |name, value|
475
236
 
476
- value
477
- end
478
-
479
- def compact
480
- value = super
237
+ value = value.split("|") if String === value and value.index "|"
481
238
 
482
- annotation_types.each do |mod|
483
- value.extend mod unless mod === value
484
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
239
+ annotation_values[name] = value
485
240
  end
486
241
 
487
- value.context = self.context
488
- value.container = self.container
242
+ object.instance_variable_set(:@annotation_values, annotation_values)
489
243
 
490
- value.extend AnnotatedArray if AnnotatedArray === self
244
+ object.reset
491
245
 
492
- value
246
+ object
493
247
  end
494
-
495
- def uniq
496
- value = super
497
-
498
- annotation_types.each do |mod|
499
- value.extend mod unless mod === value
500
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
501
- end
502
248
 
503
- value.context = self.context
504
- value.container = self.container
505
-
506
- value.extend AnnotatedArray if AnnotatedArray === self
507
-
508
- value
509
- end
249
+ def setup(object, *values)
250
+ return object if object.nil?
510
251
 
511
- def flatten
512
- value = super.dup
252
+ object.extend self
253
+ object.extend AnnotatedArray if Array === object
254
+ object.instance_variable_set(:@annotation_types, nil)
513
255
 
514
- annotation_types.each do |mod|
515
- value.extend mod unless mod === value
516
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
256
+ if Hash === (hash = values.last)
257
+ clean_and_setup_hash(object, hash)
258
+ else
259
+ setup_positional(object, *values)
517
260
  end
518
261
 
519
- value.context = self.context
520
- value.container = self.container
521
-
522
- value.extend AnnotatedArray if AnnotatedArray === self
523
-
524
- value
262
+ object
525
263
  end
526
264
 
527
- def reverse
528
- value = super
529
-
530
- annotation_types.each do |mod|
531
- value.extend mod unless mod === value
532
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
533
- end
534
-
535
- value.context = self.context
536
- value.container = self.container
537
-
538
- value.extend AnnotatedArray if AnnotatedArray === self
539
-
540
- value
265
+ def fast_setup(object, hash, shared = false)
266
+ object.extend self
267
+ object.extend AnnotatedArray if Array === object
268
+ object.instance_variable_set(:@annotation_values, hash)
269
+ object.instance_variable_set(:@shared_annotations, true) if shared
541
270
  end
542
271
 
543
- def sort_by(&block)
544
- value = super &block
545
-
546
- annotation_types.each do |mod|
547
- value.extend mod unless mod === value
548
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
272
+ def self.extended(object)
273
+ object.module_eval do
274
+ include Annotated
549
275
  end
550
-
551
- value.context = self.context
552
- value.container = self.container
553
-
554
- value.extend AnnotatedArray if AnnotatedArray === self
555
-
556
- value
557
276
  end
558
277
 
559
- def sort(&block)
560
- value = self.collect.sort(&block).collect{|value| value.respond_to?(:clean_annotations) ? value.clean_annotations.dup : value.dup }
278
+ def included(mod)
279
+ mod.instance_variable_set(:@annotations, self.annotations.dup)
280
+ mod.instance_variable_set(:@masked_annotations, self.masked_annotations.dup)
281
+ end
282
+ end
561
283
 
562
- annotation_types.each do |mod|
563
- value.extend mod unless mod === value
564
- mod.annotations.each do |annotation| value.send(annotation.to_s + "=", self.send(annotation)) end
565
- end
566
284
 
567
- value.extend AnnotatedArray if AnnotatedArray === self
285
+ if __FILE__ == $0
568
286
 
569
- value
287
+ module Gene
288
+ extend Annotation
289
+ annotation :format, :organism
570
290
  end
571
291
 
572
- def select_by(method)
573
- case
574
- when (Symbol === method or String === method)
575
- method = self.send(method)
576
- when Array === method
577
- method = method.dup
578
- else
579
- raise "Unknown format of method: of class #{method.class}"
580
- end
292
+ a = %w(1 2 3 4 5 6 6)
293
+ Gene.setup a, "Ensembl Gene ID", "Hsa"
581
294
 
582
- value = []
583
-
584
- super do |e|
585
- value << e if method.shift
586
- end
295
+ puts a.reject{|a| a.to_i < 6}.collect{|e| e.format}
587
296
 
588
- value.extend AnnotatedArray if AnnotatedArray === self
589
-
590
- value
591
- end
592
-
593
- def self.annotate(list)
594
- list[0].annotate list unless AnnotatedArray === list or list[0].nil? or (not list[0].respond_to? :annotate)
595
- end
297
+ puts
596
298
 
299
+ puts a.reject{|a| a.to_i < 6}.uniq.collect{|e| e.format}
597
300
  end
598
-