rmtools 1.1.10 → 1.1.11

Sign up to get free protection for your applications and to get access to all the features.
data/Manifest.txt CHANGED
@@ -93,8 +93,8 @@ lib/rmtools/conversions/enum.rb
93
93
  lib/rmtools/conversions/int.rb
94
94
  lib/rmtools/enumerable.rb
95
95
  lib/rmtools_notrace.rb
96
+ lib/rmtools_safe.rb
96
97
  lib/rmtools_nodebug.rb
97
- lib/rmtools_no_b.rb
98
98
  ./Rakefile
99
99
  ./Manifest.txt
100
100
  ./License.txt
data/README.txt CHANGED
@@ -8,6 +8,12 @@ Methods for basic classes addon collection.
8
8
 
9
9
  == CHANGES
10
10
 
11
+ === Version 1.1.11
12
+
13
+ * Fixed Hash#unify_keys for 1.9.2
14
+ * Speeded Array#uniq_by up
15
+ * Added some shortcut methods for ActiveRecord::Base
16
+
11
17
  === Version 1.1.10
12
18
 
13
19
  * Some bugfixes for previous updates
data/Rakefile CHANGED
@@ -2,7 +2,7 @@ require 'rake'
2
2
  require 'lib/rmtools/install'
3
3
  compile_manifest
4
4
 
5
- RMTOOLS_VERSION = '1.1.10'
5
+ RMTOOLS_VERSION = '1.1.11'
6
6
  begin
7
7
  require 'hoe'
8
8
  config = Hoe.spec 'rmtools' do
data/ext/rmtools.cpp CHANGED
@@ -193,21 +193,28 @@ static VALUE rb_str_conjunction(VALUE self, VALUE str)
193
193
  * => [8, 5]
194
194
  * a
195
195
  * => [8, 5]
196
+ * Here is implyied that callback block is +clean function+
196
197
  */
197
198
  static VALUE rb_ary_uniq_by_bang(VALUE ary)
198
199
  {
199
200
  if (!rb_block_given_p())
200
201
  return rb_ary_new4(RARRAY_LEN(ary), RARRAY_PTR(ary));
201
- VALUE hash, res;
202
+ VALUE hash, res_hash, res, el;
202
203
  long i, j;
203
204
 
204
205
  hash = rb_hash_new();
206
+ res_hash = rb_hash_new();
205
207
  for (i=j=0; i<RARRAY_LEN(ary); i++) {
206
- res = rb_yield(RARRAY_PTR(ary)[i]);
207
- if (!st_lookup(RHASH_TBL(hash), res, 0)) {
208
- rb_ary_store(ary, j++, RARRAY_PTR(ary)[i]);
209
- rb_hash_aset(hash, res, RARRAY_PTR(ary)[i]);
210
- }
208
+ // We store an element itself and so we won't calculate function of it
209
+ // other time we'll find it in source. Ruby store function is very fast,
210
+ // so we can neglect its runtime even if source array is allready uniq
211
+ el = RARRAY_PTR(ary)[i];
212
+ if (st_lookup(RHASH_TBL(hash), el, 0)) continue;
213
+ res = rb_yield(el);
214
+ if (st_lookup(RHASH_TBL(res_hash), res, 0)) continue;
215
+ rb_hash_aset(hash, el, Qtrue);
216
+ rb_hash_aset(res_hash, res, Qtrue);
217
+ rb_ary_store(ary, j++, el);
211
218
  }
212
219
  ARY_SET_LEN(ary, j);
213
220
 
@@ -400,12 +407,14 @@ static VALUE rb_hash_map_pairs(VALUE hash)
400
407
  */
401
408
  static VALUE rb_math_factorial(VALUE x)
402
409
  {
403
- if (FIX2LONG(x) < 2) return x;
404
- return rb_big_mul(x, rb_math_factorial(LONG2FIX(FIX2LONG(x) - 1)));
410
+ long a = FIX2LONG(x);
411
+ for (int i = 2; i < a; i++)
412
+ x = TYPE(x) == T_BIGNUM ?
413
+ rb_big_mul(x, rb_int2big(i)) :
414
+ rb_big_mul(rb_int2big(FIX2LONG(x)), rb_int2big(i));
415
+ return x;
405
416
  }
406
417
 
407
-
408
-
409
418
  static int unsigned_big_lte(VALUE x, VALUE y)
410
419
  {
411
420
  long xlen = RBIGNUM_LEN(x);
@@ -26,6 +26,7 @@ module ActiveRecord
26
26
  end
27
27
 
28
28
  def to_hash
29
+ return attributes if respond_to? :attributes
29
30
  serializer = Serializer.new(self)
30
31
  serializer.respond_to?(:attributes_hash) ?
31
32
  serializer.attributes_hash :
@@ -33,9 +34,22 @@ module ActiveRecord
33
34
  end
34
35
 
35
36
  alias :delete_with_id :delete
36
- # a problem was: model.delete() won't work if it has no id. Just delete() it if has
37
- def delete
38
- id ? delete_with_id : self.class.delete_all(attributes)
37
+ alias :destroy_with_id :destroy
38
+ # by default model.delete() and model.destroy() won't work if model has no id
39
+ def delete(field=nil)
40
+ id ?
41
+ delete_with_id :
42
+ field ?
43
+ self.class.delete_all(field => __send__(field)) :
44
+ self.class.delete_all(attributes)
45
+ end
46
+
47
+ def destroy(field=nil)
48
+ id ?
49
+ destroy_with_id :
50
+ field ?
51
+ self.class.destroy_all(field => __send__(field)) :
52
+ self.class.destroy_all(attributes)
39
53
  end
40
54
 
41
55
  def self.merge_conditions(*conditions)
@@ -47,6 +61,21 @@ module ActiveRecord
47
61
  "(#{segments.join(') AND (')})" unless segments.empty?
48
62
  end
49
63
 
64
+ def self.execute_sanitized(sql)
65
+ connection.execute sanitize_sql sql
66
+ end
67
+
68
+ # requires primary key
69
+ def self.forced_create(hash)
70
+ names = columns.names
71
+ id = (hash[primary_key.to_sym] ||= maximum(primary_key)+1)
72
+ execute_sanitized([
73
+ "INSERT INTO #{quoted_table_name} VALUES (:#{names*', :'})",
74
+ Hash[names.map {|name| [name.to_sym, nil]}].merge(hash)
75
+ ])
76
+ find_by_sql(["SELECT * FROM #{quoted_table_name} WHERE #{primary_key} = ?", id])[0]
77
+ end
78
+
50
79
  end
51
80
 
52
81
  end
@@ -17,4 +17,5 @@ module RMTools
17
17
  puts "#{output ? "res: #{res.size > 1000 ? res[0...1000]+"…" : res}\n" : "size of res string: #{res.to_s.size}, "}one: #{Painter.gray '%0.4fms'%[(t2-t1).to_f/ts]}, total: #{Painter.gray "#{(t2-t1).to_f}ms"}"
18
18
  end
19
19
 
20
+ module_function :timer
20
21
  end
@@ -18,7 +18,7 @@ class Array
18
18
  case top
19
19
  when Numeric; ratio = max.to_f/top
20
20
  when Array; ratio = zip(top).map {|a,b| b ? a.to_f/b : 0}.max
21
- else raise TypeError, "number or array of numbers expceted, #{top.class} given"
21
+ else raise TypeError, "number or array of numbers expected, #{top.class} given"
22
22
  end
23
23
  map {|e| e/ratio}
24
24
  end
@@ -20,14 +20,20 @@ unless defined? RMTools::Iterators
20
20
  if match = (meth = method.to_s).match(RMTools::Iterators)
21
21
  iterator, meth = match[1..2]
22
22
  meth = meth.to_sym
23
- return send(iterator) {|i| i.__send__ meth, *args, &block}
23
+ begin return send(iterator) {|i| i.__send__ meth, *args, &block}
24
+ rescue NoMethodError => e
25
+ e.message << " (`#{method}' interpreted as decorator-function `#{meth}')"
26
+ raise e
27
+ end
24
28
  elsif meth.sub!(/sses([!?]?)$/, 'ss\1') or meth.sub!(/ies([!?]?)$/, 'y\1') or meth.sub!(/s([!?]?)$/, '\1')
25
- return map {|i| i.__send__ meth.to_sym, *args, &block}
26
- else
27
- throw_no method
28
- end
29
- rescue NoMethodError
30
- throw_no method
29
+ meth = meth.to_sym
30
+ begin return map {|i| i.__send__ meth, *args, &block}
31
+ rescue NoMethodError => e
32
+ e.message << " (`#{method}' interpreted as map-function `#{meth}')"
33
+ raise e
34
+ end
35
+ else throw_no method
36
+ end
31
37
  end
32
38
  end
33
39
 
@@ -8,6 +8,20 @@ class Hash
8
8
  merge(other_hash || {})
9
9
  end
10
10
 
11
+ if RUBY_VERSION >= '1.9.2'
12
+ def unify_keys
13
+ keys.each {|k|
14
+ if k.is String
15
+ sk = k.to_sym
16
+ self[sk] = self[k] if !self[sk]
17
+ elsif k.is Symbol
18
+ sk = k.to_s
19
+ self[sk] = self[k] if !self[sk]
20
+ end
21
+ }
22
+ self
23
+ end
24
+ else
11
25
  def unify_keys
12
26
  each {|k, v|
13
27
  if k.is String
@@ -19,6 +33,7 @@ class Hash
19
33
  end
20
34
  }
21
35
  end
36
+ end
22
37
 
23
38
  def max_by_key; [(m = keys.max), self[m]] end
24
39
 
@@ -42,11 +42,11 @@ class Range
42
42
  (self.begin <=> range.begin).b || self.include_end.end <=> range.include_end.end
43
43
  end
44
44
 
45
- def include_end()
45
+ def include_end
46
46
  exclude_end? ? self.begin..(self.end - 1) : self
47
47
  end
48
48
 
49
- def center()
49
+ def center
50
50
  (first + last + (!exclude_end?).to_i)/2
51
51
  end
52
52
 
@@ -54,7 +54,7 @@ class Range
54
54
  first + (i-1)*size/j .. first - 1 + i*size/j unless i < 1 or j < 1 or j < i
55
55
  end
56
56
 
57
- def size()
57
+ def size
58
58
  last - first + (!exclude_end?).to_i
59
59
  end
60
60
 
@@ -92,6 +92,13 @@ class Range
92
92
  select {|i| i%2 == 0}
93
93
  end
94
94
 
95
+ def sum
96
+ ie = include_end.end
97
+ return (1..ie).sum - (0..-self.begin).sum if self.begin < 0
98
+ return 0 if ie < self.begin
99
+ ie*(ie+1)/2 - (1..self.begin-1).sum
100
+ end
101
+
95
102
  end
96
103
 
97
104
  class XRange
data/lib/rmtools/fs/io.rb CHANGED
@@ -48,9 +48,9 @@ module RMTools
48
48
  if File.file?(df)
49
49
  File.open(df, File::RDONLY) {|f| f.read}
50
50
  else
51
- STDERR.puts "couldn't read from #{df.inspect}; file missed"
51
+ warn "couldn't read from #{df.inspect}; file missed"
52
52
  end
53
53
  end
54
54
 
55
- module_function :rw, :write, :read
55
+ module_function :read, :write, :rw
56
56
  end
@@ -45,6 +45,6 @@ module RMTools
45
45
  STDERR.puts "#{df} is missed!"
46
46
  end
47
47
  end
48
-
48
+
49
49
  module_function :tail, :tail_n, :read_lines
50
50
  end
data/lib/rmtools/load.rb CHANGED
@@ -11,9 +11,3 @@ module RMTools
11
11
  '../rmtools.so'
12
12
  ].each {|file| RMTools::require file}
13
13
  end
14
-
15
- # Comment out in case of any method conflicts
16
- # Library methods use module functions explicitly
17
- class Object; include RMTools end
18
-
19
- # default logger now initialized in debug/logging
@@ -3,12 +3,29 @@ require 'strscan'
3
3
 
4
4
  class StringScanner
5
5
  attr_reader :last
6
+ __init__
6
7
 
8
+ # #each( <Regexp>, { <0..255> => ->{|self|}, ... } )
9
+ # #each( <Regexp>, [ [ <Regexp>, ->{|self, <MatchData>|} ], ... ] )
10
+ # #each( <Regexp> ) {|self|}
11
+ # Example:
12
+ # ss = StringScanner.new xpath
13
+ # ss.each %r{\[-?\d+\]|\{[^\}]+\}},
14
+ # ?[ => lambda {|ss|
15
+ # if node; node = FindByIndex[node, nslist, ss]
16
+ # else return [] end },
17
+ # ?{ => lambda {|ss|
18
+ # if node; node = FindByProc[node, nslist, ss]
19
+ # else return [] end },
20
+ # nil => lambda {|str|
21
+ # node = node.is(Array) ?
22
+ # node.sum {|n| n.__find(str, nslist).to_a} : node.__find(str, nslist)
23
+ # }
7
24
  def each(re, cbs=nil, &cb)
8
25
  @last = 0
9
26
  res = scan_until re
10
27
  if cbs
11
- if cbs.keys.compact[0].is Fixnum
28
+ if cbs.is Hash
12
29
  while res
13
30
  if cb = cbs[matched.ord]
14
31
  cb[self]
@@ -17,27 +34,30 @@ class StringScanner
17
34
  else break
18
35
  end
19
36
  end
37
+ if !eos? and cb = cbs[nil]
38
+ cb[tail]
39
+ end
20
40
  else
21
41
  while res
22
- if cb = cbs.find {|pattern, proc| pattern and pattern.in matched}
23
- # patterns must be as explicit as possible
24
- cb[1][self]
42
+ if cb = cbs.find {|pair| pair[0] and matched[pair[0]]}
43
+ # patterns should be as explicit as possible
44
+ cb[1][self, $~]
25
45
  @last = pos
26
46
  res = !eos? && scan_until(re)
27
47
  else break
28
48
  end
29
49
  end
50
+ if !eos? and cb = cbs.find {|pair| pair[0].nil?}
51
+ cb[1][tail]
52
+ end
30
53
  end
31
54
  else
32
55
  while res
33
- cb[self]
34
- @last = pos
35
- res = !eos? && scan_until(re)
56
+ cb[self]
57
+ @last = pos
58
+ res = !eos? && scan_until(re)
36
59
  end
37
60
  end
38
- if (cb = cbs[nil]) and !eos?
39
- cb[tail]
40
- end
41
61
  end
42
62
 
43
63
  def head
data/lib/rmtools.rb CHANGED
@@ -4,4 +4,6 @@ $__MAIN__ = self
4
4
  require 'rmtools/load'
5
5
  RMTools::require 'b'
6
6
  RMTools::require 'debug'
7
- RMTools::require 'console'
7
+ RMTools::require 'console'
8
+
9
+ unless defined? Rails; class Object; include RMTools end end
File without changes
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rmtools
3
3
  version: !ruby/object:Gem::Version
4
- hash: 7
4
+ hash: 5
5
5
  prerelease:
6
6
  segments:
7
7
  - 1
8
8
  - 1
9
- - 10
10
- version: 1.1.10
9
+ - 11
10
+ version: 1.1.11
11
11
  platform: ruby
12
12
  authors:
13
13
  - Shinku
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-03-24 00:00:00 +03:00
18
+ date: 2011-04-03 00:00:00 +04:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
@@ -173,8 +173,8 @@ files:
173
173
  - lib/rmtools/conversions/int.rb
174
174
  - lib/rmtools/enumerable.rb
175
175
  - lib/rmtools_notrace.rb
176
+ - lib/rmtools_safe.rb
176
177
  - lib/rmtools_nodebug.rb
177
- - lib/rmtools_no_b.rb
178
178
  - ./Rakefile
179
179
  - ./Manifest.txt
180
180
  - ./License.txt