rsruby 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README +102 -0
- data/examples/arrayfields.rb +36 -0
- data/examples/bioc.rb +99 -0
- data/examples/dataframe.rb +15 -0
- data/examples/erobj.rb +16 -0
- data/ext/rsruby/Converters.c +657 -0
- data/ext/rsruby/Converters.h +74 -0
- data/ext/rsruby/R_eval.c +138 -0
- data/ext/rsruby/R_eval.h +40 -0
- data/ext/rsruby/extconf.rb +20 -0
- data/ext/rsruby/robj.c +169 -0
- data/ext/rsruby/rsruby.c +183 -0
- data/ext/rsruby/rsruby.h +80 -0
- data/lib/rsruby.rb +361 -0
- data/lib/rsruby/dataframe.rb +77 -0
- data/lib/rsruby/erobj.rb +97 -0
- data/lib/rsruby/robj.rb +58 -0
- data/test/tc_array.rb +58 -0
- data/test/tc_boolean.rb +27 -0
- data/test/tc_cleanup.rb +22 -0
- data/test/tc_eval.rb +15 -0
- data/test/tc_init.rb +0 -0
- data/test/tc_io.rb +60 -0
- data/test/tc_library.rb +20 -0
- data/test/tc_modes.rb +212 -0
- data/test/tc_robj.rb +87 -0
- data/test/tc_sigint.rb +10 -0
- data/test/tc_to_r.rb +146 -0
- data/test/tc_to_ruby.rb +155 -0
- data/test/tc_util.rb +19 -0
- data/test/tc_vars.rb +28 -0
- metadata +89 -0
data/test/tc_robj.rb
ADDED
@@ -0,0 +1,87 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require 'rsruby'
|
3
|
+
|
4
|
+
unless $r
|
5
|
+
$r = RSRuby.instance
|
6
|
+
end
|
7
|
+
|
8
|
+
class TestRObj < Test::Unit::TestCase
|
9
|
+
|
10
|
+
def setup
|
11
|
+
RSRuby.set_default_mode(RSRuby::NO_DEFAULT)
|
12
|
+
$r.class_table.clear
|
13
|
+
$r.proc_table.clear
|
14
|
+
end
|
15
|
+
|
16
|
+
def test_type
|
17
|
+
assert_equal($r.array.class, RObj)
|
18
|
+
end
|
19
|
+
|
20
|
+
def test_call
|
21
|
+
#TODO
|
22
|
+
end
|
23
|
+
|
24
|
+
def test_keyword_parameters
|
25
|
+
#TODO - In RPy keyword parameters are converted like the method calls
|
26
|
+
#In ruby this isn't such a problem because you can use quoted strings
|
27
|
+
#but we will implement it anyway.
|
28
|
+
$r.list.autoconvert(RSRuby::BASIC_CONVERSION)
|
29
|
+
d = $r.list(:foo => 'foo', :bar_foo => 'bar.foo', :print_ => 'print', :as_data_frame => 'as.data.frame')
|
30
|
+
d.each do |k,v|
|
31
|
+
assert_equal(k, d[k])
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
def test_bad_keyword_parameters
|
36
|
+
#TODO?
|
37
|
+
#assert_raises(ArgumentError){$r.list(:none => 1)}
|
38
|
+
end
|
39
|
+
|
40
|
+
def test_name_conversions
|
41
|
+
assert_equal($r.array, $r['array'])
|
42
|
+
assert_equal($r.print_,$r['print'])
|
43
|
+
assert_equal($r.as_data_frame, $r['as.data.frame'])
|
44
|
+
assert_equal($r.attr__, $r['attr<-'])
|
45
|
+
end
|
46
|
+
|
47
|
+
def test_not_found
|
48
|
+
assert_raises(RException){$r.foo}
|
49
|
+
end
|
50
|
+
|
51
|
+
def test_name_length_one
|
52
|
+
assert_nothing_raised{$r.T}
|
53
|
+
end
|
54
|
+
|
55
|
+
def test_autoconvert
|
56
|
+
$r.seq.autoconvert(RSRuby::BASIC_CONVERSION)
|
57
|
+
assert_equal($r.seq(10), (1..10).to_a)
|
58
|
+
$r.seq.autoconvert(RSRuby::NO_CONVERSION)
|
59
|
+
assert_equal($r.seq(10).class, RObj)
|
60
|
+
end
|
61
|
+
|
62
|
+
def test_bad_autoconvert
|
63
|
+
assert_raises(ArgumentError){$r.seq.autoconvert(RSRuby::TOP_CONVERSION+1)}
|
64
|
+
end
|
65
|
+
|
66
|
+
def test_get_autoconvert
|
67
|
+
$r.seq.autoconvert(RSRuby::BASIC_CONVERSION)
|
68
|
+
mode = $r.seq.autoconvert
|
69
|
+
assert_equal(mode, RSRuby::BASIC_CONVERSION)
|
70
|
+
end
|
71
|
+
|
72
|
+
def test_r_gc
|
73
|
+
#TODO - How can this work?
|
74
|
+
$r.seq.autoconvert(RSRuby::NO_CONVERSION)
|
75
|
+
arr = $r.seq(100000)
|
76
|
+
$r.gc
|
77
|
+
assert($r['['].call(arr,10))
|
78
|
+
end
|
79
|
+
|
80
|
+
def test_lcall
|
81
|
+
RSRuby.set_default_mode(RSRuby::NO_CONVERSION)
|
82
|
+
arr = $r.c.lcall([['',0],['a',1],['b',2],['c',3]])
|
83
|
+
RSRuby.set_default_mode(RSRuby::BASIC_CONVERSION)
|
84
|
+
assert_equal($r.names(arr), ['','a','b','c'])
|
85
|
+
end
|
86
|
+
|
87
|
+
end
|
data/test/tc_sigint.rb
ADDED
data/test/tc_to_r.rb
ADDED
@@ -0,0 +1,146 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require 'rsruby'
|
3
|
+
|
4
|
+
unless $r
|
5
|
+
$r = RSRuby.instance
|
6
|
+
end
|
7
|
+
|
8
|
+
class Foo
|
9
|
+
end
|
10
|
+
|
11
|
+
class Bar
|
12
|
+
def initialize(x)
|
13
|
+
@x = x
|
14
|
+
end
|
15
|
+
def as_r
|
16
|
+
@x
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
class TestToR < Test::Unit::TestCase
|
21
|
+
|
22
|
+
def setup
|
23
|
+
RSRuby.set_default_mode(RSRuby::NO_DEFAULT)
|
24
|
+
end
|
25
|
+
|
26
|
+
def test_robj_to_r
|
27
|
+
|
28
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
29
|
+
|
30
|
+
r1 = $r.c(4)
|
31
|
+
r2 = $r.c('foo')
|
32
|
+
r3 = $r.c(['a','b'])
|
33
|
+
|
34
|
+
assert($r['=='].call(r1,4))
|
35
|
+
assert($r['=='].call(r2,'foo'))
|
36
|
+
assert($r['=='].call(r3,['a','b']))
|
37
|
+
|
38
|
+
assert_equal($r.typeof($r.eval),'closure')
|
39
|
+
assert_equal($r.typeof($r.eval($r.eval)), 'closure')
|
40
|
+
assert_equal($r.typeof($r.eval([$r.eval,$r.eval])), 'list')
|
41
|
+
|
42
|
+
#Same tests as above in basic mode - should be identical
|
43
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
44
|
+
|
45
|
+
r1 = $r.c(4)
|
46
|
+
r2 = $r.c('foo')
|
47
|
+
r3 = $r.c(['a','b'])
|
48
|
+
|
49
|
+
assert($r['=='].call(r1,4))
|
50
|
+
assert($r['=='].call(r2,'foo'))
|
51
|
+
assert($r['=='].call(r3,['a','b']))
|
52
|
+
|
53
|
+
assert_equal($r.typeof($r.eval),'closure')
|
54
|
+
assert_equal($r.typeof($r.eval($r.eval)), 'closure')
|
55
|
+
assert_equal($r.typeof($r.eval([$r.eval,$r.eval])), 'list')
|
56
|
+
|
57
|
+
end
|
58
|
+
|
59
|
+
def test_empty_array_to_null
|
60
|
+
assert($r.is_null([]))
|
61
|
+
end
|
62
|
+
|
63
|
+
def test_boolean_to_logical
|
64
|
+
assert_equal($r.c(true),true)
|
65
|
+
assert_equal($r.c(true).class,true.class)
|
66
|
+
assert_equal($r.c(false),false)
|
67
|
+
assert_equal($r.c(false).class,false.class)
|
68
|
+
end
|
69
|
+
|
70
|
+
def test_int_to_int
|
71
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
72
|
+
assert_equal($r.typeof($r.c(4)), 'integer')
|
73
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
74
|
+
assert_equal($r.typeof($r.c(4)), 'integer')
|
75
|
+
end
|
76
|
+
|
77
|
+
def test_float_to_float
|
78
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
79
|
+
assert_equal($r.typeof($r.c(4.5)), 'double')
|
80
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
81
|
+
assert_equal($r.typeof($r.c(4.5)), 'double')
|
82
|
+
end
|
83
|
+
|
84
|
+
def test_char_to_char
|
85
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
86
|
+
assert_equal($r.typeof($r.c('foo')), 'character')
|
87
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
88
|
+
assert_equal($r.typeof($r.c('foo')), 'character')
|
89
|
+
end
|
90
|
+
|
91
|
+
def test_hash_to_named_vector
|
92
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
93
|
+
assert_equal($r.typeof($r.c(:foo => 5, :bar => 7)),'integer')
|
94
|
+
assert($r.attributes($r.c(:foo => 5, :bar => 7))['names'].include?('foo'))
|
95
|
+
assert($r.attributes($r.c(:foo => 5, :bar => 7))['names'].include?('bar'))
|
96
|
+
#TODO - these fail because of the different calling semantics in
|
97
|
+
#RSRuby
|
98
|
+
#$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
99
|
+
#assert_equal($r.typeof($r.c(:foo => 5, :bar => 7)),'integer')
|
100
|
+
#assert($r.attributes($r.c(:foo => 5, :bar => 7))['names'].include?('foo'))
|
101
|
+
#assert($r.attributes($r.c(:foo => 5, :bar => 7))['names'].include?('bar'))
|
102
|
+
end
|
103
|
+
|
104
|
+
def test_array_to_vector
|
105
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
106
|
+
assert_equal($r.length($r.c(1,2,3,4)),4)
|
107
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
108
|
+
assert_equal($r.length($r.c(1,2,3,4)),4)
|
109
|
+
end
|
110
|
+
|
111
|
+
def test_not_convertible
|
112
|
+
#TODO - range?
|
113
|
+
assert_raises(ArgumentError){$r.c(1..10)}
|
114
|
+
end
|
115
|
+
|
116
|
+
def test_instances_not_convertible
|
117
|
+
foo = Foo.new
|
118
|
+
assert_raises(ArgumentError){$r.c(foo)}
|
119
|
+
end
|
120
|
+
|
121
|
+
def test_as_r_method
|
122
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
123
|
+
|
124
|
+
a = Bar.new(3)
|
125
|
+
b = Bar.new('foo')
|
126
|
+
d = Bar.new($r.seq)
|
127
|
+
|
128
|
+
assert_equal($r.c(a),3)
|
129
|
+
assert_equal($r.c(b),'foo')
|
130
|
+
assert_equal($r.c(d).call(1,3),[1,2,3])
|
131
|
+
|
132
|
+
end
|
133
|
+
|
134
|
+
def test_max_int_to_r
|
135
|
+
#TODO
|
136
|
+
end
|
137
|
+
|
138
|
+
def test_inf_to_r
|
139
|
+
#TODO
|
140
|
+
end
|
141
|
+
|
142
|
+
def test_NaN_to_r
|
143
|
+
#TODO
|
144
|
+
end
|
145
|
+
|
146
|
+
end
|
data/test/tc_to_ruby.rb
ADDED
@@ -0,0 +1,155 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require 'rsruby'
|
3
|
+
|
4
|
+
unless $r
|
5
|
+
$r = RSRuby.instance
|
6
|
+
end
|
7
|
+
|
8
|
+
class TestToRuby < Test::Unit::TestCase
|
9
|
+
|
10
|
+
def setup
|
11
|
+
RSRuby.set_default_mode(RSRuby::NO_DEFAULT)
|
12
|
+
$r.seq.autoconvert(RSRuby::BASIC_CONVERSION)
|
13
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
14
|
+
end
|
15
|
+
|
16
|
+
def test_null_to_nil
|
17
|
+
assert($r.attributes($r.seq).nil?)
|
18
|
+
end
|
19
|
+
|
20
|
+
def test_factor_to_list
|
21
|
+
assert_equal($r.factor([1,2,3,4]), ['1','2','3','4'])
|
22
|
+
assert_equal($r.factor([1,1,1,2]), ['1','1','1','2'])
|
23
|
+
assert_equal($r.factor(['a','b','c']), ['a','b','c'])
|
24
|
+
end
|
25
|
+
|
26
|
+
def test_NA_int
|
27
|
+
#The formula on right should equal smallest Fixnum
|
28
|
+
#in current Ruby build (can vary)
|
29
|
+
assert_equal($r.NA, (-1)*(2**((1.size*8)-1)))
|
30
|
+
assert($r.is_na($r.NA))
|
31
|
+
end
|
32
|
+
|
33
|
+
def test_NA_string
|
34
|
+
assert_equal($r.eval_R('as.character(NA)'), 'NA')
|
35
|
+
assert_equal($r.as_character($r.NA), 'NA')
|
36
|
+
assert_equal($r.as_character($r.NaN), 'NaN')
|
37
|
+
end
|
38
|
+
|
39
|
+
def test_factor_NA
|
40
|
+
assert_equal($r.factor($r.NA) , 'NA')
|
41
|
+
assert_equal($r.factor($r.NaN), 'NaN')
|
42
|
+
assert_equal($r.factor($r.as_character('NA')), 'NA')
|
43
|
+
|
44
|
+
xi = [1,2,$r.NA,$r.NaN,4]
|
45
|
+
assert_equal($r.factor(xi), ['1','2','NA','NaN','4'])
|
46
|
+
|
47
|
+
xd = [1.01,2.02,$r.NA,$r.NaN,4.04]
|
48
|
+
assert_equal($r.factor(xd), ['1.01','2.02','NA','NaN','4.04'])
|
49
|
+
|
50
|
+
end
|
51
|
+
|
52
|
+
def test_NA_list
|
53
|
+
|
54
|
+
#TODO - RPy has commented out these tests as well.
|
55
|
+
#The conversion between NA/NaN and Ruby seems a little confused
|
56
|
+
#at the moment
|
57
|
+
|
58
|
+
xi = [1,2,$r.NA,$r.NaN,4]
|
59
|
+
assert_equal($r.as_character(xi), ['1','2','NA','NaN','4'])
|
60
|
+
#assert_equal($r.as_numeric(xi) , [1.0,2.0,$r.NA,$r.NaN,4.0])
|
61
|
+
#assert_equal($r.as_integer(xi) , [1,2,$r.NA,$r.NaN,4])
|
62
|
+
assert_equal($r.factor(xi) , ['1','2','NA','NaN','4'])
|
63
|
+
assert_equal($r.is_na(xi) , [false, false, true, true, false])
|
64
|
+
|
65
|
+
xd = [1.01,2.02,$r.NA,$r.NaN,4.04]
|
66
|
+
assert_equal($r.as_character(xd), ['1.01','2.02','NA','NaN','4.04'])
|
67
|
+
#assert_equal($r.as_numeric(xi) , [1.01,2.01,$r.NA,$r.NaN,4.01])
|
68
|
+
assert_equal($r.as_integer(xd) , [1,2,$r.NA,$r.NA,4])
|
69
|
+
assert_equal($r.factor(xd) , ['1.01','2.02','NA','NaN','4.04'])
|
70
|
+
assert_equal($r.is_na(xd) , [false, false, true, true, false])
|
71
|
+
end
|
72
|
+
|
73
|
+
#TODO - table.txt?????????
|
74
|
+
def test_dataframe_to_list
|
75
|
+
$r.read_table.autoconvert(RSRuby::BASIC_CONVERSION)
|
76
|
+
assert_equal($r.read_table('test/table.txt', {:header => 1}),
|
77
|
+
{
|
78
|
+
'A' => ['X1','X2','X3'],
|
79
|
+
'C' => [5,8,2],
|
80
|
+
'B' => [4.0,7.0,6.0],
|
81
|
+
'D' => ['6','9','Foo']
|
82
|
+
})
|
83
|
+
end
|
84
|
+
|
85
|
+
def test_logical_to_boolean
|
86
|
+
assert_equal($r.TRUE, true)
|
87
|
+
assert_equal($r.T, true)
|
88
|
+
assert_equal($r.FALSE, false)
|
89
|
+
assert_equal($r.F, false)
|
90
|
+
end
|
91
|
+
|
92
|
+
def test_int_to_int
|
93
|
+
assert_equal($r.as_integer(5),5)
|
94
|
+
assert_equal($r.as_integer(-3),-3)
|
95
|
+
end
|
96
|
+
|
97
|
+
def test_float_to_float
|
98
|
+
assert_equal($r.as_real(5),5.0)
|
99
|
+
assert_equal($r.as_real(3.1),3.1)
|
100
|
+
assert_equal($r.as_real(-3.1), -3.1)
|
101
|
+
end
|
102
|
+
|
103
|
+
def test_complex_to_complex
|
104
|
+
#TODO - Think about Complex support
|
105
|
+
assert_equal($r.as_complex(Complex(1,2)), Complex(1,2))
|
106
|
+
assert_equal($r.as_complex(Complex(1.5,-3.4)), Complex(1.5,-3.4))
|
107
|
+
end
|
108
|
+
|
109
|
+
def test_str_to_str
|
110
|
+
$r.as_data_frame.autoconvert(RSRuby::NO_CONVERSION)
|
111
|
+
assert_equal($r.class_($r.as_data_frame([1,2,3])), 'data.frame')
|
112
|
+
end
|
113
|
+
|
114
|
+
def test_vector_length_one
|
115
|
+
assert_equal($r.c(1),1)
|
116
|
+
assert_equal($r.c('foo'),'foo')
|
117
|
+
end
|
118
|
+
|
119
|
+
def test_int_vector_to_array
|
120
|
+
assert_equal($r.seq(10),[1,2,3,4,5,6,7,8,9,10])
|
121
|
+
end
|
122
|
+
|
123
|
+
def test_float_vector_to_array
|
124
|
+
assert_equal($r.seq(1,2,{:by => 0.5}), [1.0,1.5,2.0])
|
125
|
+
end
|
126
|
+
|
127
|
+
def test_complex_vector_to_array
|
128
|
+
assert_equal($r.c(Complex(1,2),Complex(2,-3)),[Complex(1,2),Complex(2,-3)])
|
129
|
+
end
|
130
|
+
|
131
|
+
def test_str_vector_to_array
|
132
|
+
assert_equal($r.c('Foo','Bar'),['Foo','Bar'])
|
133
|
+
end
|
134
|
+
|
135
|
+
def test_list_to_array
|
136
|
+
$r.list.autoconvert(RSRuby::BASIC_CONVERSION)
|
137
|
+
assert_equal($r.list(1,2.0,'foo'),[1,2.0,'foo'])
|
138
|
+
end
|
139
|
+
|
140
|
+
def test_named_vector_to_hash
|
141
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
142
|
+
a = $r.attr__($r.c(1,2,3), 'names', ['foo','bar','baz'])
|
143
|
+
assert_equal(a,{'foo'=>1,'bar'=>2,'baz'=>3})
|
144
|
+
assert_equal($r.list(:foo => 1, :bar => 2, :baz => 3),{'foo'=>1,'bar'=>2,'baz'=>3})
|
145
|
+
end
|
146
|
+
|
147
|
+
def test_vector_coercion
|
148
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
149
|
+
assert_equal($r.typeof($r.c(1,2,3)), 'integer')
|
150
|
+
assert_equal($r.typeof($r.c(1,2.0,3)), 'double')
|
151
|
+
assert_equal($r.typeof($r.c(1,Complex(2,3),3)), 'complex')
|
152
|
+
assert_equal($r.typeof($r.c(1,'foo',3)), 'character')
|
153
|
+
end
|
154
|
+
|
155
|
+
end
|
data/test/tc_util.rb
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require 'rsruby'
|
3
|
+
|
4
|
+
class TestUtil < Test::Unit::TestCase
|
5
|
+
|
6
|
+
def test_as_list
|
7
|
+
#TODO
|
8
|
+
#assert_equal($r.as_lis
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_with_mode
|
12
|
+
#TODO
|
13
|
+
end
|
14
|
+
|
15
|
+
def test_r_code
|
16
|
+
#TODO - Not sure about this. I use r.eval_R('')
|
17
|
+
#Not really a util
|
18
|
+
end
|
19
|
+
end
|
data/test/tc_vars.rb
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require 'rsruby'
|
3
|
+
|
4
|
+
unless $r
|
5
|
+
$r = RSRuby.instance
|
6
|
+
end
|
7
|
+
|
8
|
+
class TestVars < Test::Unit::TestCase
|
9
|
+
|
10
|
+
def test_get_vars
|
11
|
+
$r.eval_R("f<-function(x) x+1")
|
12
|
+
$r.assign('x',100)
|
13
|
+
$r.assign('v',(1..10).to_a)
|
14
|
+
#There is a difference here between RPy and us
|
15
|
+
#a final hash argument is treated as named arguments
|
16
|
+
#to the original function call (assign) not as a list
|
17
|
+
#to be given to the function
|
18
|
+
$r.c.autoconvert(RSRuby::NO_CONVERSION)
|
19
|
+
$r.assign('d',$r.c({'a' => 1, 'b' => 2}))
|
20
|
+
$r.c.autoconvert(RSRuby::BASIC_CONVERSION)
|
21
|
+
|
22
|
+
assert_equal($r.x, 100)
|
23
|
+
assert_equal($r.v, (1..10).to_a)
|
24
|
+
assert_equal($r.d, $r.c({'a' => 1, 'b' => 2}))
|
25
|
+
assert_equal($r.f.class, $r.c.class)
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|