fuzzy-logic 0.0.1 → 0.0.2
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/Gemfile.lock +1 -1
- data/README.md +66 -1
- data/lib/fuzzy-logic/generate.rb +42 -0
- data/lib/fuzzy-logic.rb +1 -1
- data/spec/fuzzy-logic/generate_spec.rb +107 -0
- metadata +5 -5
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
@@ -21,7 +21,72 @@ Or install it yourself as:
|
|
21
21
|
|
22
22
|
## Usage
|
23
23
|
|
24
|
-
|
24
|
+
### A simple Fuzzy-Set
|
25
|
+
|
26
|
+
require 'fuzzy-logic'
|
27
|
+
|
28
|
+
its_near_christmas = FuzzyLogic::Set.new(1) { |time|
|
29
|
+
# default output is zero
|
30
|
+
o = 0.0
|
31
|
+
|
32
|
+
# time has to be in december before or at the 24th
|
33
|
+
if time.month == 12 and time.day <= 24 then
|
34
|
+
# set is completly true when its 20th december or above
|
35
|
+
o = 1.0 if time.day >= 20
|
36
|
+
|
37
|
+
# set is fuzzy when its between 6th and 19th
|
38
|
+
o = 1.0 - (24.0 - time.day)/(24.0 - 6.0) if time.day >= 6 and time.day < 20.0
|
39
|
+
end
|
40
|
+
|
41
|
+
# just the correct return
|
42
|
+
o
|
43
|
+
}
|
44
|
+
|
45
|
+
its_near_christmas.get( Time.now )
|
46
|
+
|
47
|
+
its_near_christmas.support( Time.new(2013, 12, 8) ) # => true
|
48
|
+
its_near_christmas.support( Time.new(2013, 12, 6) ) # => false
|
49
|
+
|
50
|
+
tis_near_christmas.core( Time.new(2013, 12, 23) ) # => true
|
51
|
+
its_near_christmas.core( Time.new(2013, 12, 8) ) # => false
|
52
|
+
|
53
|
+
### Use Fuzzy-Generators
|
54
|
+
|
55
|
+
The return is a normal Fuzzy-Set
|
56
|
+
|
57
|
+
require 'fuzzy-logic'
|
58
|
+
|
59
|
+
# generate a triangle
|
60
|
+
triangle = FuzzyLogic::Generate.triangle(10, 4) # range is (8..12) and mid is 10 (8 and 12 is zero)
|
61
|
+
|
62
|
+
# generate a trapezoid
|
63
|
+
trapez = FuzzyLogic::Generate.trapezoid(10, 20, 30, 40) # ~support(10..40) and core(20..30)
|
64
|
+
|
65
|
+
# combinations
|
66
|
+
triangle_and_trapez = FuzzyLogic::Generate.and(triangle, trapez)
|
67
|
+
triangle_or_trapez = FuzzyLogic::Generate.or( triangle, trapez)
|
68
|
+
not_in_trapez = FuzzyLogic::Generate.not( trapez )
|
69
|
+
|
70
|
+
### Use Fuzzy-Collection
|
71
|
+
|
72
|
+
require 'fuzzy-logic'
|
73
|
+
|
74
|
+
temp = FuzzyLogic::Collection.new("temperature in °C") { |testvalue|
|
75
|
+
o = true
|
76
|
+
if not testvalue.is_a? Numeric then
|
77
|
+
o = false
|
78
|
+
elsif testvalue > 100 or testvalue < -100 then
|
79
|
+
o = false
|
80
|
+
end
|
81
|
+
o
|
82
|
+
}
|
83
|
+
|
84
|
+
temp[:hot] = FuzzyLogic::Generate.trapezoid(25, 35, 100, 101)
|
85
|
+
temp[:cold] = FuzzyLogic::Generate.trapezoid(-101, -100, 5, 15)
|
86
|
+
temp[:cool_to_warm] = FuzzyLogic::Generate.and( FuzzyLogic::Generate.not(temp[:hot]), FuzzyLogic::Generate.not(temp[:cold]))
|
87
|
+
|
88
|
+
temp.get(20)
|
89
|
+
# => { :cool_to_warm => 1.0 }
|
25
90
|
|
26
91
|
## Contributing
|
27
92
|
|
data/lib/fuzzy-logic/generate.rb
CHANGED
@@ -65,6 +65,48 @@ module FuzzyLogic
|
|
65
65
|
args_test_array_filled_with_arrays_length(args, "Arguments of a list fuzzy-set should be Arrays of length 2", 2)
|
66
66
|
end
|
67
67
|
|
68
|
+
def self.or(seta, setb, soft=false)
|
69
|
+
raise ArgumentError, "Arguments should be fuzzy-sets" unless seta.is_a? Set and setb.is_a? Set
|
70
|
+
|
71
|
+
h1 = seta.height || 0
|
72
|
+
h2 = setb.height || 0
|
73
|
+
|
74
|
+
hmax = [h1,h2].max
|
75
|
+
hmax = hmax > 0 ? hmax : nil
|
76
|
+
|
77
|
+
if soft then
|
78
|
+
return Set.new(hmax) { |n|
|
79
|
+
seta.get(n) + setb.get(n) - seta.get(n) * setb.get(n)
|
80
|
+
}
|
81
|
+
end
|
82
|
+
|
83
|
+
return Set.new(hmax) { |n|
|
84
|
+
[seta.get(n), setb.get(n)].max
|
85
|
+
}
|
86
|
+
end
|
87
|
+
|
88
|
+
def self.and(seta, setb, soft=false)
|
89
|
+
raise ArgumentError, "Arguments should be fuzzy-sets" unless seta.is_a? Set and setb.is_a? Set
|
90
|
+
|
91
|
+
if soft then
|
92
|
+
return Set.new { |n|
|
93
|
+
seta.get(n) * setb.get(n)
|
94
|
+
}
|
95
|
+
end
|
96
|
+
|
97
|
+
return Set.new { |n|
|
98
|
+
[seta.get(n), setb.get(n)].min
|
99
|
+
}
|
100
|
+
end
|
101
|
+
|
102
|
+
def self.not(seta)
|
103
|
+
raise ArgumentError, "Argument should be a fuzzy-set" unless seta.is_a? Set
|
104
|
+
|
105
|
+
return Set.new { |n|
|
106
|
+
1 - seta.get(n)
|
107
|
+
}
|
108
|
+
end
|
109
|
+
|
68
110
|
private
|
69
111
|
|
70
112
|
def self.args_test_array_filled_with_arrays_length(args, msg, len)
|
data/lib/fuzzy-logic.rb
CHANGED
@@ -72,4 +72,111 @@ describe FuzzyLogic::Generate do
|
|
72
72
|
describe "a list fuzzy-set" do
|
73
73
|
# no test yet - no architecture ...
|
74
74
|
end
|
75
|
+
|
76
|
+
describe "combination of fuzzy-sets" do
|
77
|
+
before do
|
78
|
+
@seta = FuzzyLogic::Generate.trapezoid(10,20,30,40)
|
79
|
+
@setb = FuzzyLogic::Generate.trapezoid(30,40,50,60)
|
80
|
+
end
|
81
|
+
|
82
|
+
describe "or-combination" do
|
83
|
+
before do
|
84
|
+
@set_or = FuzzyLogic::Generate.or(@seta, @setb)
|
85
|
+
@set_or_soft = FuzzyLogic::Generate.or(@seta, @setb, true)
|
86
|
+
end
|
87
|
+
|
88
|
+
it "should raise an ArgumentError on Arguments, which are not a Set" do
|
89
|
+
lambda { FuzzyLogic::Generate.or(@seta, 1) }.must_raise ArgumentError
|
90
|
+
lambda { FuzzyLogic::Generate.or(:test, @setb) }.must_raise ArgumentError
|
91
|
+
end
|
92
|
+
|
93
|
+
it "should have a height of one" do
|
94
|
+
@set_or.height.must_equal 1
|
95
|
+
@set_or_soft.height.must_equal 1
|
96
|
+
end
|
97
|
+
|
98
|
+
it "should return a fuzzy-set" do
|
99
|
+
FuzzyLogic::Generate.or(@seta, @setb).must_be :is_a?, FuzzyLogic::Set
|
100
|
+
end
|
101
|
+
|
102
|
+
it "should have values of one" do
|
103
|
+
[20, 25, 30, 40, 45, 50].each { |i|
|
104
|
+
@set_or.get(i).must_equal 1
|
105
|
+
}
|
106
|
+
end
|
107
|
+
|
108
|
+
it "should have values of zero" do
|
109
|
+
[0, 5, 10, 60, 65, 70].each { |i|
|
110
|
+
@set_or.get(i).must_equal 0
|
111
|
+
}
|
112
|
+
end
|
113
|
+
|
114
|
+
it "should have values between one and zero" do
|
115
|
+
[11,15,19,31,35,39,51,59].each { |i|
|
116
|
+
@set_or.get(i).must_be :>, 0
|
117
|
+
@set_or.get(i).must_be :<, 1
|
118
|
+
}
|
119
|
+
end
|
120
|
+
|
121
|
+
it "can handle a soft mode" do
|
122
|
+
@set_or_soft.get(35).must_be :>, 0.5
|
123
|
+
@set_or_soft.get(35).must_equal 0.75
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
describe "and-combination" do
|
128
|
+
before do
|
129
|
+
@set_and = FuzzyLogic::Generate.and(@seta, @setb)
|
130
|
+
@set_and_soft = FuzzyLogic::Generate.and(@seta, @setb, true)
|
131
|
+
end
|
132
|
+
|
133
|
+
it "should raise an ArgumentError on Arguments, which are not a Set" do
|
134
|
+
lambda { FuzzyLogic::Generate.and(@seta, 1) }.must_raise ArgumentError
|
135
|
+
lambda { FuzzyLogic::Generate.and(:test, @setb) }.must_raise ArgumentError
|
136
|
+
end
|
137
|
+
|
138
|
+
it "should return a fuzzy-set" do
|
139
|
+
FuzzyLogic::Generate.and(@seta, @setb).must_be :is_a?, FuzzyLogic::Set
|
140
|
+
end
|
141
|
+
|
142
|
+
it "should have values with 0.5/0.25" do
|
143
|
+
@set_and.get(35).must_equal 0.5
|
144
|
+
@set_and_soft.get(35).must_equal 0.25
|
145
|
+
end
|
146
|
+
|
147
|
+
it "should have values with 0" do
|
148
|
+
[20,30,40,50].each { |i|
|
149
|
+
@set_and.get(i).must_equal 0
|
150
|
+
@set_and_soft.get(i).must_equal 0
|
151
|
+
}
|
152
|
+
end
|
153
|
+
|
154
|
+
it "should have values between 0 and 0.5" do
|
155
|
+
(31..39).to_a.each { |i|
|
156
|
+
@set_and.get(i).must_be :>, 0
|
157
|
+
@set_and.get(i).must_be :<=, 0.5
|
158
|
+
}
|
159
|
+
end
|
160
|
+
end
|
161
|
+
|
162
|
+
describe "not-combination" do
|
163
|
+
before do
|
164
|
+
@set_not = FuzzyLogic::Generate.not(@seta)
|
165
|
+
end
|
166
|
+
|
167
|
+
it "should raise an ArgumentError when argument is not a Set" do
|
168
|
+
lambda { FuzzyLogic::Generate.not(1) }.must_raise ArgumentError
|
169
|
+
end
|
170
|
+
|
171
|
+
it "should return a fuzzy-set" do
|
172
|
+
FuzzyLogic::Generate.not(@seta).must_be :is_a?, FuzzyLogic::Set
|
173
|
+
end
|
174
|
+
|
175
|
+
it "should be the oposite (1-val)" do
|
176
|
+
(0..100).to_a.each { |i|
|
177
|
+
@set_not.get(i).must_equal (1 - @seta.get(i))
|
178
|
+
}
|
179
|
+
end
|
180
|
+
end
|
181
|
+
end
|
75
182
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: fuzzy-logic
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.2
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -13,7 +13,7 @@ date: 2013-01-15 00:00:00.000000000 Z
|
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: guard-minitest
|
16
|
-
requirement: &
|
16
|
+
requirement: &85026750 !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: :development
|
23
23
|
prerelease: false
|
24
|
-
version_requirements: *
|
24
|
+
version_requirements: *85026750
|
25
25
|
- !ruby/object:Gem::Dependency
|
26
26
|
name: rb-inotify
|
27
|
-
requirement: &
|
27
|
+
requirement: &85026490 !ruby/object:Gem::Requirement
|
28
28
|
none: false
|
29
29
|
requirements:
|
30
30
|
- - ~>
|
@@ -32,7 +32,7 @@ dependencies:
|
|
32
32
|
version: 0.8.8
|
33
33
|
type: :development
|
34
34
|
prerelease: false
|
35
|
-
version_requirements: *
|
35
|
+
version_requirements: *85026490
|
36
36
|
description: fuzzy-logic and fuzzy-rules are really handy for some problems.
|
37
37
|
email:
|
38
38
|
- ae@writedown.eu
|