boolean-expression 0.0.1 → 0.0.1.1
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/lib/boolean/expression.rb +107 -114
- data/lib/boolean/expression/group.rb +3 -3
- data/lib/boolean/expression/logic.rb +19 -20
- data/lib/boolean/expression/name.rb +3 -3
- metadata +18 -27
data/lib/boolean/expression.rb
CHANGED
|
@@ -22,120 +22,113 @@ unless defined?(Boolean)
|
|
|
22
22
|
end
|
|
23
23
|
|
|
24
24
|
class Boolean::Expression
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
a, logic, b = values.shift(3)
|
|
133
|
-
|
|
134
|
-
values.unshift(logic.evaluate(a, b))
|
|
135
|
-
end
|
|
136
|
-
|
|
137
|
-
values.first
|
|
138
|
-
end
|
|
25
|
+
def self.parse (text)
|
|
26
|
+
base = Group.new
|
|
27
|
+
name = nil
|
|
28
|
+
stack = [base]
|
|
29
|
+
logic = nil
|
|
30
|
+
|
|
31
|
+
text.to_s.chars.each_with_index {|char, index|
|
|
32
|
+
begin
|
|
33
|
+
if char == ')' && stack.length == 1
|
|
34
|
+
raise SyntaxError, 'closing an unopened parenthesis'
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
if char.match(/\s|\(|\)/) || (!logic && ['|', '&', '!'].member?(char))
|
|
38
|
+
if logic || (name && name.match(/(and|or|not)/i))
|
|
39
|
+
stack.last << Logic.new(logic || name)
|
|
40
|
+
logic = nil
|
|
41
|
+
name = nil
|
|
42
|
+
elsif name
|
|
43
|
+
stack.last << Name.new(name)
|
|
44
|
+
name = nil
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
if name || logic
|
|
49
|
+
name << char if name
|
|
50
|
+
logic << char if logic
|
|
51
|
+
else
|
|
52
|
+
case char
|
|
53
|
+
when '(' then stack.push Group.new
|
|
54
|
+
when ')' then stack[-2] << stack.pop
|
|
55
|
+
when '|' then logic = '|'
|
|
56
|
+
when '&' then logic = '&'
|
|
57
|
+
when '!' then stack.last << Logic.new('!')
|
|
58
|
+
else name = char if !char.match(/\s/)
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
rescue SyntaxError => e
|
|
62
|
+
raise "#{e.message} near `#{text[index - 4, 8]}` at character #{index}"
|
|
63
|
+
end
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
raise SyntaxError, 'not all parenthesis are closed' if stack.length != 1
|
|
67
|
+
|
|
68
|
+
raise SyntaxError, 'the expression cannot end with a logic operator' if logic
|
|
69
|
+
|
|
70
|
+
base << Name.new(name) if name
|
|
71
|
+
|
|
72
|
+
base = base.first if base.length == 1 && base.first.is_a?(Group)
|
|
73
|
+
|
|
74
|
+
new(base)
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
def self.[] (*args)
|
|
78
|
+
parse(*args)
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
attr_reader :base
|
|
82
|
+
|
|
83
|
+
def initialize (base = Group.new)
|
|
84
|
+
@base = base
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
def evaluate (*args)
|
|
88
|
+
_evaluate(@base, args.flatten.compact.map {|piece|
|
|
89
|
+
piece.to_s
|
|
90
|
+
})
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
alias [] evaluate
|
|
94
|
+
|
|
95
|
+
def to_s
|
|
96
|
+
@base.inspect
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
private
|
|
100
|
+
def _evaluate (group, pieces)
|
|
101
|
+
return false if pieces.empty?
|
|
102
|
+
|
|
103
|
+
values = []
|
|
104
|
+
|
|
105
|
+
group.each {|thing|
|
|
106
|
+
case thing
|
|
107
|
+
when Logic then values << thing
|
|
108
|
+
when Group then values << _evaluate(thing, pieces)
|
|
109
|
+
when Name then values << pieces.member?(thing.to_s)
|
|
110
|
+
end
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
at = 0
|
|
114
|
+
while at < values.length
|
|
115
|
+
if values[at].is_a?(Logic) && values[at].type == :not
|
|
116
|
+
value = values.delete_at(at + 1)
|
|
117
|
+
|
|
118
|
+
values[at] = !(value.is_a?(Group) ? value.evaluate(values[at]) : value)
|
|
119
|
+
end
|
|
120
|
+
|
|
121
|
+
at += 1
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
while values.length > 1
|
|
125
|
+
a, logic, b = values.shift(3)
|
|
126
|
+
|
|
127
|
+
values.unshift(logic.evaluate(a, b))
|
|
128
|
+
end
|
|
129
|
+
|
|
130
|
+
values.first
|
|
131
|
+
end
|
|
139
132
|
end
|
|
140
133
|
|
|
141
134
|
require 'boolean/expression/name'
|
|
@@ -18,27 +18,26 @@
|
|
|
18
18
|
#++
|
|
19
19
|
|
|
20
20
|
class Boolean::Expression::Logic
|
|
21
|
-
|
|
21
|
+
attr_reader :type
|
|
22
22
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
23
|
+
def initialize (what)
|
|
24
|
+
@type = case what
|
|
25
|
+
when '!', /not/i then :not
|
|
26
|
+
when '&&', /and/i then :and
|
|
27
|
+
when '||', /or/i then :or
|
|
28
|
+
else raise SyntaxError, 'invalid logical operator, logical fallacies everywhere'
|
|
29
|
+
end
|
|
30
|
+
end
|
|
29
31
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
+
def evaluate (a, b=nil)
|
|
33
|
+
case @type
|
|
34
|
+
when :not then !a
|
|
35
|
+
when :and then !!(a && b)
|
|
36
|
+
when :or then !!(a || b)
|
|
37
|
+
end
|
|
38
|
+
end
|
|
32
39
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
when :and then !!(a && b)
|
|
37
|
-
when :or then !!(a || b)
|
|
38
|
-
end
|
|
39
|
-
end
|
|
40
|
-
|
|
41
|
-
def inspect
|
|
42
|
-
self.type.to_s.upcase
|
|
43
|
-
end
|
|
40
|
+
def inspect
|
|
41
|
+
type.to_s.upcase
|
|
42
|
+
end
|
|
44
43
|
end
|
metadata
CHANGED
|
@@ -1,57 +1,48 @@
|
|
|
1
|
-
--- !ruby/object:Gem::Specification
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: boolean-expression
|
|
3
|
-
version: !ruby/object:Gem::Version
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 0.0.1.1
|
|
4
5
|
prerelease:
|
|
5
|
-
version: 0.0.1
|
|
6
6
|
platform: ruby
|
|
7
|
-
authors:
|
|
7
|
+
authors:
|
|
8
8
|
- meh.
|
|
9
9
|
autorequire:
|
|
10
10
|
bindir: bin
|
|
11
11
|
cert_chain: []
|
|
12
|
-
|
|
13
|
-
date: 2011-06-22 00:00:00 Z
|
|
12
|
+
date: 2012-01-28 00:00:00.000000000 Z
|
|
14
13
|
dependencies: []
|
|
15
|
-
|
|
16
14
|
description:
|
|
17
15
|
email: meh@paranoici.org
|
|
18
16
|
executables: []
|
|
19
|
-
|
|
20
17
|
extensions: []
|
|
21
|
-
|
|
22
18
|
extra_rdoc_files: []
|
|
23
|
-
|
|
24
|
-
files:
|
|
19
|
+
files:
|
|
25
20
|
- lib/boolean/expression.rb
|
|
26
21
|
- lib/boolean/expression/logic.rb
|
|
27
22
|
- lib/boolean/expression/name.rb
|
|
28
23
|
- lib/boolean/expression/group.rb
|
|
29
24
|
homepage: http://github.com/meh/boolean-expression
|
|
30
25
|
licenses: []
|
|
31
|
-
|
|
32
26
|
post_install_message:
|
|
33
27
|
rdoc_options: []
|
|
34
|
-
|
|
35
|
-
require_paths:
|
|
28
|
+
require_paths:
|
|
36
29
|
- lib
|
|
37
|
-
required_ruby_version: !ruby/object:Gem::Requirement
|
|
30
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
38
31
|
none: false
|
|
39
|
-
requirements:
|
|
40
|
-
- -
|
|
41
|
-
- !ruby/object:Gem::Version
|
|
42
|
-
version:
|
|
43
|
-
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
32
|
+
requirements:
|
|
33
|
+
- - ! '>='
|
|
34
|
+
- !ruby/object:Gem::Version
|
|
35
|
+
version: '0'
|
|
36
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
44
37
|
none: false
|
|
45
|
-
requirements:
|
|
46
|
-
- -
|
|
47
|
-
- !ruby/object:Gem::Version
|
|
48
|
-
version:
|
|
38
|
+
requirements:
|
|
39
|
+
- - ! '>='
|
|
40
|
+
- !ruby/object:Gem::Version
|
|
41
|
+
version: '0'
|
|
49
42
|
requirements: []
|
|
50
|
-
|
|
51
43
|
rubyforge_project:
|
|
52
|
-
rubygems_version: 1.8.
|
|
44
|
+
rubygems_version: 1.8.10
|
|
53
45
|
signing_key:
|
|
54
46
|
specification_version: 3
|
|
55
47
|
summary: A simple library to evaluate boolean expressions.
|
|
56
48
|
test_files: []
|
|
57
|
-
|