ml 0.1.1 → 0.2.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/VERSION +1 -1
- data/lib/method/adaptive_perceptron.rb +26 -0
- data/lib/method/perceptron.rb +36 -17
- data/lib/ml.rb +1 -0
- data/ml.gemspec +3 -2
- data/spec/learner_spec.rb +22 -4
- metadata +18 -17
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.2.0
|
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'matrix'
|
2
|
+
|
3
|
+
module ML
|
4
|
+
module Learner
|
5
|
+
# Implementation of Adaptive Perceptron Learning Algorithm
|
6
|
+
class AdaptivePerceptronLearner < PerceptronLearner
|
7
|
+
# Initialize an adaptive perceptron learner
|
8
|
+
#
|
9
|
+
# @param [Integer] dim the number of dimension
|
10
|
+
# @param [Float] the eta parameter
|
11
|
+
def initialize dim, eta
|
12
|
+
super(dim)
|
13
|
+
@eta = eta
|
14
|
+
end
|
15
|
+
|
16
|
+
protected
|
17
|
+
def wrongly_classify x, y
|
18
|
+
classify(x) * y <= 1
|
19
|
+
end
|
20
|
+
|
21
|
+
def update_vector x, y
|
22
|
+
@w = @w + @eta * (y - classify(x))* x
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
data/lib/method/perceptron.rb
CHANGED
@@ -7,7 +7,7 @@ module ML
|
|
7
7
|
# Initialize a perceptron learner
|
8
8
|
#
|
9
9
|
# @param [Integer] dim the number of dimension
|
10
|
-
def initialize dim
|
10
|
+
def initialize dim, thres = 1.0/0
|
11
11
|
@dim = dim
|
12
12
|
@w = Matrix.column_vector(Array.new(dim + 1, 0))
|
13
13
|
end
|
@@ -15,25 +15,43 @@ module ML
|
|
15
15
|
# Train with supervised data
|
16
16
|
#
|
17
17
|
# @param [Hash] data supervised input data (mapping from array to integer)
|
18
|
-
|
19
|
-
|
18
|
+
# @param [Numeric] threshold the upper bound of the traning iteration
|
19
|
+
# @return [Array] error_and_update [error, update] error in traning and update numbers used
|
20
|
+
def train! data, threshold = 1.0/0
|
21
|
+
pool = data.to_a
|
22
|
+
update = 0
|
23
|
+
error = 0
|
24
|
+
|
20
25
|
while true
|
26
|
+
break if update >= threshold
|
21
27
|
misclassified = false
|
28
|
+
order = (1...(pool.size)).to_a.shuffle
|
22
29
|
|
23
|
-
for
|
30
|
+
for i in order
|
31
|
+
dat, result = pool[i]
|
24
32
|
aug_data = Matrix.column_vector(dat)
|
25
33
|
|
26
|
-
if
|
34
|
+
if wrongly_classify aug_data, result
|
27
35
|
misclassified = true
|
28
36
|
|
29
|
-
|
30
|
-
|
37
|
+
update_vector aug_data, result
|
38
|
+
update += 1
|
31
39
|
break
|
32
40
|
end
|
33
41
|
end
|
34
42
|
|
35
43
|
break unless misclassified
|
36
44
|
end
|
45
|
+
|
46
|
+
# check out errors
|
47
|
+
if update >= threshold
|
48
|
+
for dat, result in pool
|
49
|
+
classified_result = (classify(Matrix.column_vector(dat)) <=> 0)
|
50
|
+
error += 1 unless result == classified_result
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
[error, update]
|
37
55
|
end
|
38
56
|
|
39
57
|
# The final coefficient of the line
|
@@ -43,24 +61,25 @@ module ML
|
|
43
61
|
@w.column(0).to_a
|
44
62
|
end
|
45
63
|
|
46
|
-
# The number for updates
|
47
|
-
#
|
48
|
-
# @return [Integer] update count
|
49
|
-
def update_count
|
50
|
-
@update
|
51
|
-
end
|
52
|
-
|
53
64
|
# Predict certain data
|
54
65
|
#
|
55
66
|
# @param [Array] data data in question
|
56
67
|
# @return [Integer] prediction
|
57
68
|
def predict data
|
58
|
-
classify
|
69
|
+
classify(Matrix.column_vector(data + [1.0])) <=> 0
|
59
70
|
end
|
60
71
|
|
61
|
-
|
72
|
+
protected
|
62
73
|
def classify data
|
63
|
-
(@w.transpose * data)[0,0]
|
74
|
+
(@w.transpose * data)[0,0]
|
75
|
+
end
|
76
|
+
|
77
|
+
def wrongly_classify x, y
|
78
|
+
classify(x) * y <= 0
|
79
|
+
end
|
80
|
+
|
81
|
+
def update_vector x, y
|
82
|
+
@w = @w + y * x
|
64
83
|
end
|
65
84
|
end
|
66
85
|
end
|
data/lib/ml.rb
CHANGED
data/ml.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = "ml"
|
8
|
-
s.version = "0.
|
8
|
+
s.version = "0.2.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Andrew Liu"]
|
12
|
-
s.date = "2011-10-
|
12
|
+
s.date = "2011-10-17"
|
13
13
|
s.description = "Machine learning library in Ruby"
|
14
14
|
s.email = "andrewliu33@gmail.com"
|
15
15
|
s.extra_rdoc_files = [
|
@@ -26,6 +26,7 @@ Gem::Specification.new do |s|
|
|
26
26
|
"lib/data/generator.rb",
|
27
27
|
"lib/data/parser.rb",
|
28
28
|
"lib/data/plotter.rb",
|
29
|
+
"lib/method/adaptive_perceptron.rb",
|
29
30
|
"lib/method/perceptron.rb",
|
30
31
|
"lib/ml.rb",
|
31
32
|
"ml.gemspec",
|
data/spec/learner_spec.rb
CHANGED
@@ -8,13 +8,13 @@ describe "Learner" do
|
|
8
8
|
generator = ML::Data::Generator2D.new
|
9
9
|
data = generator.points_2d(10)
|
10
10
|
|
11
|
-
learner.train! data
|
11
|
+
error, update_count = learner.train! data
|
12
12
|
|
13
13
|
line = learner.line
|
14
14
|
line.should.kind_of?(Array).should == true
|
15
15
|
line.size.should == 3
|
16
16
|
|
17
|
-
|
17
|
+
update_count.should > 0
|
18
18
|
end
|
19
19
|
|
20
20
|
it "should run perceptron learning in hyperspace" do
|
@@ -23,13 +23,31 @@ describe "Learner" do
|
|
23
23
|
generator = ML::Data::Generator.new(4)
|
24
24
|
data = generator.points(10, ML::Data::Generator.generate_vector(4))
|
25
25
|
|
26
|
-
learner.train! data
|
26
|
+
error, update_count = learner.train! data
|
27
27
|
|
28
28
|
line = learner.line
|
29
29
|
line.should.kind_of?(Array).should == true
|
30
30
|
line.size.should == 5
|
31
31
|
|
32
|
-
|
32
|
+
update_count.should > 0
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
describe "Adpative Perceptron Learner" do
|
37
|
+
it "should run adaptive perceptron learning in hyperspace" do
|
38
|
+
learner = ML::Learner::AdaptivePerceptronLearner.new(4, 0.1)
|
39
|
+
|
40
|
+
generator = ML::Data::Generator.new(4)
|
41
|
+
data = generator.points(10, ML::Data::Generator.generate_vector(4))
|
42
|
+
|
43
|
+
error, update_count = learner.train! data, 1000
|
44
|
+
|
45
|
+
line = learner.line
|
46
|
+
line.should.kind_of?(Array).should == true
|
47
|
+
line.size.should == 5
|
48
|
+
|
49
|
+
update_count.should > 0
|
50
|
+
update_count.should < 1000
|
33
51
|
end
|
34
52
|
end
|
35
53
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ml
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2011-10-
|
12
|
+
date: 2011-10-17 00:00:00.000000000Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: rubyvis
|
16
|
-
requirement: &
|
16
|
+
requirement: &2157025440 !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>='
|
@@ -21,10 +21,10 @@ dependencies:
|
|
21
21
|
version: '0'
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
|
-
version_requirements: *
|
24
|
+
version_requirements: *2157025440
|
25
25
|
- !ruby/object:Gem::Dependency
|
26
26
|
name: nokogiri
|
27
|
-
requirement: &
|
27
|
+
requirement: &2157024740 !ruby/object:Gem::Requirement
|
28
28
|
none: false
|
29
29
|
requirements:
|
30
30
|
- - ! '>='
|
@@ -32,10 +32,10 @@ dependencies:
|
|
32
32
|
version: '0'
|
33
33
|
type: :runtime
|
34
34
|
prerelease: false
|
35
|
-
version_requirements: *
|
35
|
+
version_requirements: *2157024740
|
36
36
|
- !ruby/object:Gem::Dependency
|
37
37
|
name: bacon
|
38
|
-
requirement: &
|
38
|
+
requirement: &2157023900 !ruby/object:Gem::Requirement
|
39
39
|
none: false
|
40
40
|
requirements:
|
41
41
|
- - ! '>='
|
@@ -43,10 +43,10 @@ dependencies:
|
|
43
43
|
version: '0'
|
44
44
|
type: :development
|
45
45
|
prerelease: false
|
46
|
-
version_requirements: *
|
46
|
+
version_requirements: *2157023900
|
47
47
|
- !ruby/object:Gem::Dependency
|
48
48
|
name: yard
|
49
|
-
requirement: &
|
49
|
+
requirement: &2157022940 !ruby/object:Gem::Requirement
|
50
50
|
none: false
|
51
51
|
requirements:
|
52
52
|
- - ~>
|
@@ -54,10 +54,10 @@ dependencies:
|
|
54
54
|
version: 0.6.0
|
55
55
|
type: :development
|
56
56
|
prerelease: false
|
57
|
-
version_requirements: *
|
57
|
+
version_requirements: *2157022940
|
58
58
|
- !ruby/object:Gem::Dependency
|
59
59
|
name: bundler
|
60
|
-
requirement: &
|
60
|
+
requirement: &2157022300 !ruby/object:Gem::Requirement
|
61
61
|
none: false
|
62
62
|
requirements:
|
63
63
|
- - ~>
|
@@ -65,10 +65,10 @@ dependencies:
|
|
65
65
|
version: 1.0.0
|
66
66
|
type: :development
|
67
67
|
prerelease: false
|
68
|
-
version_requirements: *
|
68
|
+
version_requirements: *2157022300
|
69
69
|
- !ruby/object:Gem::Dependency
|
70
70
|
name: jeweler
|
71
|
-
requirement: &
|
71
|
+
requirement: &2157021360 !ruby/object:Gem::Requirement
|
72
72
|
none: false
|
73
73
|
requirements:
|
74
74
|
- - ~>
|
@@ -76,10 +76,10 @@ dependencies:
|
|
76
76
|
version: 1.6.4
|
77
77
|
type: :development
|
78
78
|
prerelease: false
|
79
|
-
version_requirements: *
|
79
|
+
version_requirements: *2157021360
|
80
80
|
- !ruby/object:Gem::Dependency
|
81
81
|
name: rcov
|
82
|
-
requirement: &
|
82
|
+
requirement: &2157020280 !ruby/object:Gem::Requirement
|
83
83
|
none: false
|
84
84
|
requirements:
|
85
85
|
- - ! '>='
|
@@ -87,7 +87,7 @@ dependencies:
|
|
87
87
|
version: '0'
|
88
88
|
type: :development
|
89
89
|
prerelease: false
|
90
|
-
version_requirements: *
|
90
|
+
version_requirements: *2157020280
|
91
91
|
description: Machine learning library in Ruby
|
92
92
|
email: andrewliu33@gmail.com
|
93
93
|
executables: []
|
@@ -105,6 +105,7 @@ files:
|
|
105
105
|
- lib/data/generator.rb
|
106
106
|
- lib/data/parser.rb
|
107
107
|
- lib/data/plotter.rb
|
108
|
+
- lib/method/adaptive_perceptron.rb
|
108
109
|
- lib/method/perceptron.rb
|
109
110
|
- lib/ml.rb
|
110
111
|
- ml.gemspec
|
@@ -126,7 +127,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
126
127
|
version: '0'
|
127
128
|
segments:
|
128
129
|
- 0
|
129
|
-
hash: -
|
130
|
+
hash: -383772979455407848
|
130
131
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
131
132
|
none: false
|
132
133
|
requirements:
|