r_type 0.0.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (47) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +17 -0
  3. data/.travis.yml +14 -0
  4. data/Gemfile +3 -0
  5. data/Guardfile +9 -0
  6. data/LICENSE.txt +22 -0
  7. data/README.md +131 -0
  8. data/Rakefile +9 -0
  9. data/bin/r_console +17 -0
  10. data/lib/r_type.rb +41 -0
  11. data/lib/r_type/convert.rb +28 -0
  12. data/lib/r_type/core_ext.rb +30 -0
  13. data/lib/r_type/core_ext/boolean_delegate_r.rb +8 -0
  14. data/lib/r_type/core_ext/delegate_checker.rb +11 -0
  15. data/lib/r_type/core_ext/numeric_delegate_r.rb +20 -0
  16. data/lib/r_type/helper.rb +4 -0
  17. data/lib/r_type/helper/matrix_multiply.rb +13 -0
  18. data/lib/r_type/helper/robj_delegatable.rb +78 -0
  19. data/lib/r_type/helper/robj_delegatable_class_methods.rb +35 -0
  20. data/lib/r_type/helper/ruby_compareable.rb +9 -0
  21. data/lib/r_type/r.rb +50 -0
  22. data/lib/r_type/type/array.rb +7 -0
  23. data/lib/r_type/type/base.rb +14 -0
  24. data/lib/r_type/type/data_frame.rb +7 -0
  25. data/lib/r_type/type/function.rb +8 -0
  26. data/lib/r_type/type/integer.rb +7 -0
  27. data/lib/r_type/type/list.rb +7 -0
  28. data/lib/r_type/type/matrix.rb +65 -0
  29. data/lib/r_type/type/numeric.rb +7 -0
  30. data/lib/r_type/type/string.rb +7 -0
  31. data/lib/r_type/type/vector.rb +10 -0
  32. data/lib/r_type/version.rb +3 -0
  33. data/r_type.gemspec +28 -0
  34. data/sample/sample1.rb +34 -0
  35. data/sample/sample2.rb +38 -0
  36. data/sample/sample3.rb +79 -0
  37. data/sample/sample4.rb +43 -0
  38. data/sample/sample5.rb +61 -0
  39. data/spec/convert_spec.rb +93 -0
  40. data/spec/core_ext/boolean_delegate_r_spec.rb +39 -0
  41. data/spec/core_ext/numeric_delegate_r_spec.rb +27 -0
  42. data/spec/helper/robj_delegatable_spec.rb +68 -0
  43. data/spec/r_spec.rb +54 -0
  44. data/spec/spec_helper.rb +34 -0
  45. data/spec/type/base_spec.rb +52 -0
  46. data/spec/type/matrix_spec.rb +157 -0
  47. metadata +196 -0
@@ -0,0 +1,35 @@
1
+ module RType
2
+ module Helper
3
+ module RObjDelegatable
4
+ module ClassMethods
5
+ def delegate_to_R *from_to
6
+ from_to_hash = from_to.first.is_a?(Hash) \
7
+ ? from_to.first \
8
+ : from_to.inject({}) {|h,x| h[x] = x; h }
9
+
10
+ from_to_hash.each do |from, to|
11
+ define_method(from) do |*args, &block|
12
+ if can_delegate_to_R?(*args)
13
+ R[to].call(self, args.first)
14
+ else
15
+ super(*args, &block)
16
+ end
17
+ end
18
+ end
19
+ end
20
+
21
+ def delegate_constructor klass, *methods
22
+ delegate_klass = self
23
+
24
+ methods.each do |name|
25
+ self.class.class_eval do
26
+ define_method(name) do |*args, &block|
27
+ delegate_klass.new klass.send(name, *args, &block)
28
+ end
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,9 @@
1
+ module RType::Helper::RubyCompareable
2
+ def == obj
3
+ if obj.is_a?(RType::Helper::Compareable)
4
+ to_ruby == obj.to_ruby
5
+ else
6
+ super
7
+ end
8
+ end
9
+ end
data/lib/r_type/r.rb ADDED
@@ -0,0 +1,50 @@
1
+ module RType
2
+ module R
3
+ class << self
4
+ def method_missing name, *args, &block
5
+ if name =~ /^(.*)=$/
6
+ rsruby[:assign].call $1.to_s, args.first
7
+ elsif rsruby.respond_to? name
8
+ rsruby.send name, *args
9
+ else
10
+ obj = rsruby[name]
11
+ if obj.is_a?(::RType::Function)
12
+ obj.call *args
13
+ else
14
+ obj
15
+ end
16
+ end
17
+ end
18
+
19
+ def run &block
20
+ instance_eval &block
21
+ end
22
+
23
+ def print *args
24
+ rsruby[:print].call *args
25
+ end
26
+
27
+ def lazy_expression r_exp
28
+ rsruby.eval_R "quote(#{r_exp})"
29
+ end
30
+ alias_method "`", :lazy_expression
31
+
32
+ def rsruby
33
+ @rsruby ||= init_rsruby
34
+ end
35
+
36
+ def init_rsruby
37
+ RSRuby.set_default_mode RSRuby::PROC_CONVERSION
38
+ converter = RType::Convert.new
39
+ @rsruby = RSRuby.instance
40
+ @rsruby.proc_table[->(x){ true }] = ->(x) { converter.convert x }
41
+ @rsruby
42
+ end
43
+
44
+ private
45
+ def reset
46
+ @rsruby = nil
47
+ end
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class Array < Base
3
+ def self.match? robj, type
4
+ type == 'array'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,14 @@
1
+ # -*- coding: utf-8 -*-
2
+ module RType
3
+ class Base < DelegateClass(RObj)
4
+ include Helper::RObjDelegatable
5
+
6
+ def self.match? robj, type
7
+ true
8
+ end
9
+
10
+ def initialize robj
11
+ @robj = robj
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class DataFrame < Base
3
+ def self.match? robj, type
4
+ type == 'data.frame'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,8 @@
1
+ module RType
2
+ class Function < Base
3
+ def self.match? robj, type
4
+ type == 'function' || (type == 'standardGeneric' &&
5
+ Convert.call_R_without_convert(:is_function, robj))
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class Integer < Numeric
3
+ def self.match? robj, type
4
+ type == 'integer'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class List < Base
3
+ def self.match? robj, type
4
+ type == 'list'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,65 @@
1
+ module RType
2
+ class Matrix < DelegateClass(::Matrix)
3
+ include Helper::RObjDelegatable
4
+ include Helper::MatrixMultiply
5
+
6
+ delegate_constructor ::Matrix, :I, :[], :build, :column_vector, :columns,
7
+ :diagonal, :empty, :identity, :row_vector,
8
+ :rows, :scalar, :unit, :zero
9
+
10
+ def self.match? robj, type
11
+ type == 'matrix'
12
+ end
13
+
14
+ def initialize obj, *args
15
+ case obj
16
+ when ::RObj
17
+ @robj = obj
18
+ when ::Matrix
19
+ @ruby_obj = obj
20
+ else
21
+ raise "Not supported: #{obj} in RType::Matrix"
22
+ end
23
+ end
24
+
25
+ def [] *args
26
+ args = convert_nil_args_to_vector(args)
27
+ R['['].call self, *args
28
+ end
29
+
30
+ def []= *args
31
+ if args[0].is_a?(RType::Matrix)
32
+ self.robj = R['[<-'].call(self, args[0], args[1]).robj
33
+ else
34
+ args = convert_nil_args_to_vector(args)
35
+ self.robj = R['[<-'].call(self, *args).robj
36
+ end
37
+ end
38
+
39
+ def row_size
40
+ R.nrow(self)
41
+ end
42
+
43
+ def column_size
44
+ R.ncol(self)
45
+ end
46
+
47
+ private
48
+ def convert_robj_to_ruby
49
+ if R.mode(self) == 'logical'
50
+ # We can't parse this R-matrix. So, we return robj instead of ruby_obj.
51
+ # TODO: Parse R-matrix that have logical values
52
+ nil
53
+ else
54
+ rows = super
55
+ ::Matrix.rows(rows.first.is_a?(::Numeric) ? [rows] : rows)
56
+ end
57
+ end
58
+
59
+ def convert_nil_args_to_vector args
60
+ args[0] = (1..row_size).to_a if args[0].nil? && args[1].is_a?(::Numeric)
61
+ args[1] = (1..column_size).to_a if args[1].nil? && args[0].is_a?(::Numeric)
62
+ args
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class Numeric < Base
3
+ def self.match? robj, type
4
+ type == 'numeric'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ module RType
2
+ class String < Base
3
+ def self.match? robj, type
4
+ type == 'character'
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,10 @@
1
+ module RType
2
+ class Vector < Base
3
+ include Helper::MatrixMultiply
4
+
5
+ def self.match? robj, type
6
+ (type == 'numeric' || type == 'integer') &&
7
+ Convert.call_R_without_convert(:length, robj) > 1
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,3 @@
1
+ module RType
2
+ VERSION = "0.0.3"
3
+ end
data/r_type.gemspec ADDED
@@ -0,0 +1,28 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'r_type/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "r_type"
8
+ spec.version = RType::VERSION
9
+ spec.authors = ["Tatsuya Takamura"]
10
+ spec.email = ["tkmr2000@gmail.com"]
11
+ spec.description = %q{RType is a wrapper library for RSRuby.}
12
+ spec.summary = %q{RType is a wrapper library for RSRuby.}
13
+ spec.homepage = "https://github.com/ttakamura"
14
+ spec.license = "MIT"
15
+
16
+ spec.files = `git ls-files`.split($/)
17
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
+ spec.require_paths = ["lib"]
20
+
21
+ spec.add_dependency "rsruby", ">= 0.5"
22
+ spec.add_development_dependency "bundler", "~> 1.3"
23
+ spec.add_development_dependency "rake"
24
+ spec.add_development_dependency "rspec", "~> 2.13.0"
25
+ spec.add_development_dependency "rspec-mocks", "~> 2.13.0"
26
+ spec.add_development_dependency "guard", "~> 1.8.0"
27
+ spec.add_development_dependency "guard-rspec", "~> 3.0.1"
28
+ end
data/sample/sample1.rb ADDED
@@ -0,0 +1,34 @@
1
+ require '../lib/r_type'
2
+
3
+ R.run do
4
+ print (cos(0) - sqrt(2)) / exp(4)
5
+
6
+ x = (1..5).to_a
7
+ print sqrt(x)
8
+ print log(x)
9
+
10
+ self.x2 = [1, 2, 3, 4, 5, 3]
11
+ self.y2 = [1, 3, 2, 4, 5, 3]
12
+ print summary(x2)
13
+ print cor(x2, y2)
14
+ print diff(y2)
15
+ print cumsum(x2)
16
+
17
+ print x2 + y2
18
+ print x2 - y2
19
+ print x2 + 10
20
+ print x2 * y2
21
+ end
22
+ # >> [1] -0.007586586
23
+ # >> [1] 1.000000 1.414214 1.732051 2.000000 2.236068
24
+ # >> [1] 0.0000000 0.6931472 1.0986123 1.3862944 1.6094379
25
+ # >> Min. 1st Qu. Median Mean 3rd Qu. Max.
26
+ # >> 1.00 2.25 3.00 3.00 3.75 5.00
27
+ # >> [1] 0.9
28
+ # >> [1] 2 -1 2 1 -2
29
+ # >> [1] 1 3 6 10 15 18
30
+ # >> [1] 2 5 5 8 10 6
31
+ # >> [1] 0 -1 1 0 0 0
32
+ # >> [1] 11 12 13 14 15 13
33
+ # >> [,1]
34
+ # >> [1,] 63
data/sample/sample2.rb ADDED
@@ -0,0 +1,38 @@
1
+ require '../lib/r_type'
2
+
3
+ R.run do
4
+ x = (0..4).to_a
5
+
6
+ double = eval_R <<-RSRC
7
+ function (x) x * 2
8
+ RSRC
9
+
10
+ print double(10)
11
+ print sapply(x, double)
12
+ pow = `function(x) x ^ 2`
13
+ print sapply(x, pow)
14
+
15
+ f = `function(x) exp(x) - 2`
16
+ print uniroot(f, [0, 1])
17
+
18
+ print polyroot([2, 3, 1])
19
+ print integrate(pow, 0, 1)
20
+ end
21
+ # >> [1] 0 0 0 0 0 0 0 0 0 0
22
+ # >> [1] 0 2 4 6 8
23
+ # >> [1] 0 1 4 9 16
24
+ # >> $root
25
+ # >> [1] 0.6931457
26
+ # >>
27
+ # >> $f.root
28
+ # >> [1] -2.943424e-06
29
+ # >>
30
+ # >> $iter
31
+ # >> [1] 5
32
+ # >>
33
+ # >> $estim.prec
34
+ # >> [1] 6.103516e-05
35
+ # >>
36
+ # >> [1] -1+0i -2-0i
37
+ # >> 0.3333333 with absolute error < 3.7e-15
38
+ # >> 0.9772499 with absolute error < 1.6e-06
data/sample/sample3.rb ADDED
@@ -0,0 +1,79 @@
1
+ require '../lib/r_type'
2
+
3
+ R.run do
4
+ print RType::Matrix.zero 3
5
+ print RType::Matrix.I 3
6
+
7
+ a = RType::Matrix[[1, 3], [2, 4]]
8
+ b = RType::Matrix[[0, 2], [1, 3]]
9
+
10
+ print t(a)
11
+ print a + b - a * b
12
+
13
+ print outer(a, b)
14
+ print kronecker(a, b)
15
+
16
+ print a * [1, 2]
17
+ print 1 / a
18
+
19
+ x = matrix (1..9).to_a, ncol: 3
20
+ print upper_tri(x)
21
+ print x
22
+ end
23
+ # >> [,1] [,2] [,3]
24
+ # >> [1,] 0 0 0
25
+ # >> [2,] 0 0 0
26
+ # >> [3,] 0 0 0
27
+ # >> [,1] [,2] [,3]
28
+ # >> [1,] 1 0 0
29
+ # >> [2,] 0 1 0
30
+ # >> [3,] 0 0 1
31
+ # >> [,1] [,2]
32
+ # >> [1,] 1 2
33
+ # >> [2,] 3 4
34
+ # >> [,1] [,2]
35
+ # >> [1,] -2 -6
36
+ # >> [2,] -1 -9
37
+ # >> , , 1, 1
38
+ # >>
39
+ # >> [,1] [,2]
40
+ # >> [1,] 0 0
41
+ # >> [2,] 0 0
42
+ # >>
43
+ # >> , , 2, 1
44
+ # >>
45
+ # >> [,1] [,2]
46
+ # >> [1,] 1 3
47
+ # >> [2,] 2 4
48
+ # >>
49
+ # >> , , 1, 2
50
+ # >>
51
+ # >> [,1] [,2]
52
+ # >> [1,] 2 6
53
+ # >> [2,] 4 8
54
+ # >>
55
+ # >> , , 2, 2
56
+ # >>
57
+ # >> [,1] [,2]
58
+ # >> [1,] 3 9
59
+ # >> [2,] 6 12
60
+ # >>
61
+ # >> [,1] [,2] [,3] [,4]
62
+ # >> [1,] 0 2 0 6
63
+ # >> [2,] 1 3 3 9
64
+ # >> [3,] 0 4 0 8
65
+ # >> [4,] 2 6 4 12
66
+ # >> [,1]
67
+ # >> [1,] 7
68
+ # >> [2,] 10
69
+ # >> [,1] [,2]
70
+ # >> [1,] 1.0 0.3333333
71
+ # >> [2,] 0.5 0.2500000
72
+ # >> [,1] [,2] [,3]
73
+ # >> [1,] FALSE TRUE TRUE
74
+ # >> [2,] FALSE FALSE TRUE
75
+ # >> [3,] FALSE FALSE FALSE
76
+ # >> [,1] [,2] [,3]
77
+ # >> [1,] 1 4 7
78
+ # >> [2,] 2 5 8
79
+ # >> [3,] 3 6 9