calc_dmoral12 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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: b25e0ce4f095aef8648db25f661a9536a13b9329
4
+ data.tar.gz: 86d24dcffdd63a544136da56af8fd02498ea4827
5
+ SHA512:
6
+ metadata.gz: 2819950e41d454e2777a37317d5bbd65e246ec1dfb6aaf8326657961b9584f79645759efddbb96e5ed033a8d54a7d5c378b955d286097c68aaa4e896c9bc4751
7
+ data.tar.gz: 3fd13c729cedd9a2eb2fd86bd6209168e6f1f7e5915a34708e2467a886fa2f9f96496ca05489cdffd2e611b01d5ccd5e1175d21b52118d2418a1898d6ba42848
data/bin/calc ADDED
@@ -0,0 +1,23 @@
1
+ #!/usr/bin/env ruby
2
+ # env busca donde esta instalado ruby
3
+ # cuerpo principal de toda la calculadora
4
+ require 'rubygems'
5
+ require 'calculator'
6
+ require 'calcex'
7
+
8
+ $stdout.print "> "
9
+ $stdout.flush
10
+
11
+ text = gets
12
+
13
+ $calc = Calculator.new()
14
+
15
+ begin
16
+ puts "= " + $calc.eval(text).to_s
17
+ rescue ParseError
18
+ puts "Parse Error"
19
+ rescue UnrecognizedTokenException
20
+ puts "UnrecognizedTokenException"
21
+ rescue
22
+ puts "Unkown exception"
23
+ end
data/lib/ast.rb ADDED
@@ -0,0 +1,86 @@
1
+ require 'set'
2
+
3
+
4
+ class BinaryNode
5
+ attr_reader :left, :right
6
+
7
+ def initialize(left,right) #inicializacion
8
+ @left = left
9
+ @right = right
10
+ end
11
+ end
12
+
13
+ class UnaryNode
14
+ attr_reader :subTree
15
+
16
+ def initialize(subTree)
17
+ @subTree = subTree
18
+ end
19
+ end
20
+
21
+ class AddNode < BinaryNode #hereda de binaryNode
22
+ def initialize(left, right)
23
+ super(left,right)
24
+ end
25
+
26
+ def evaluate()
27
+ @left.evaluate() + @right.evaluate() #los obtiene y los evalua
28
+ end
29
+ end
30
+
31
+ class SubNode < BinaryNode
32
+ def initialize(left, right)
33
+ super(left,right)
34
+ end
35
+
36
+ def evaluate()
37
+ return @left.evaluate() - @right.evaluate()
38
+ end
39
+ end
40
+
41
+ class TimesNode < BinaryNode
42
+ def initialize(left, right)
43
+ super(left,right)
44
+ end
45
+
46
+ def evaluate()
47
+ return @left.evaluate() * @right.evaluate()
48
+ end
49
+ end
50
+
51
+ class DivideNode < BinaryNode
52
+ def initialize(left, right)
53
+ super(left,right)
54
+ end
55
+
56
+ def evaluate()
57
+ return @left.evaluate() / @right.evaluate()
58
+ end
59
+ end
60
+
61
+
62
+ class StoreNode < UnaryNode #
63
+ def initialize(subTree)
64
+ super(subTree)
65
+ end
66
+
67
+ def evaluate
68
+ $calc.memory = subTree.evaluate()
69
+ end
70
+ end
71
+
72
+ class RecallNode #
73
+ def evaluate
74
+ $calc.memory
75
+ end
76
+ end
77
+
78
+ class NumNode
79
+ def initialize(num) #
80
+ @num = num
81
+ end
82
+
83
+ def evaluate()
84
+ return @num
85
+ end
86
+ end
data/lib/calcex.rb ADDED
@@ -0,0 +1,4 @@
1
+
2
+ class ParseError < Exception; end
3
+ class UnrecognizedTokenException < Exception; end
4
+ #para generar una expecion ; para poder separar el fin de la clase
data/lib/calculator.rb ADDED
@@ -0,0 +1,17 @@
1
+ require 'parser'
2
+ require 'ast'
3
+
4
+ class Calculator
5
+ attr_accessor :memory #lo cambiamos por accessor atttr_reader : memory
6
+
7
+
8
+ def initialize()
9
+ @memory = 0
10
+ end
11
+
12
+ def eval(expr)
13
+ parser = Parser.new(StringIO.new(expr))
14
+ ast = parser.parse()
15
+ return ast.evaluate()
16
+ end
17
+ end
data/lib/parser.rb ADDED
@@ -0,0 +1,138 @@
1
+ require 'ast'
2
+ require 'scanner'
3
+ require 'token'
4
+ require 'calcex'
5
+
6
+ class Parser
7
+ def initialize(istream)
8
+ @scan = Scanner.new(istream)
9
+ end
10
+
11
+ def parse()
12
+ return Prog()
13
+ end
14
+
15
+ private
16
+ def Prog()
17
+ result = Expr()
18
+ t = @scan.getToken()
19
+
20
+ if t.type != :eof then
21
+ print "Expected EOF. Found ", t.type, ".\n"
22
+ raise ParseError.new
23
+ end
24
+
25
+ return result
26
+ end
27
+
28
+ def Expr()
29
+ return RestExpr(Term())
30
+ end
31
+
32
+ def RestExpr(e)
33
+ t = @scan.getToken()
34
+
35
+ if t.type == :add then
36
+ return RestExpr(AddNode.new(e,Term()))
37
+ end
38
+
39
+ if t.type == :sub then
40
+ return RestExpr(SubNode.new(e,Term()))
41
+ end
42
+
43
+ @scan.putBackToken()
44
+
45
+ return e
46
+ end
47
+
48
+ def Term()
49
+ # # Write your Term() code here. This code is just temporary
50
+ # # so you can try the calculator out before finishing it.
51
+
52
+ # t = @scan.getToken()
53
+
54
+ # if t.type == :number then
55
+ # val = t.lex.to_i
56
+ # return NumNode.new(val)
57
+ # end
58
+
59
+ # puts "Term not implemented\n"
60
+
61
+ # raise ParseError.new
62
+ RestTerm(Storable())
63
+ end
64
+
65
+ def RestTerm(e)
66
+ # puts "RestTerm not implemented"
67
+ # raise ParseError.new # "Parse Error"
68
+
69
+ t = @scan.getToken()
70
+
71
+ if t.type == :times then
72
+ return RestTerm(TimesNode.new(e, Storable()))
73
+ end
74
+
75
+ if t.type == :divide then
76
+ return RestTerm(DivideNode.new(e, Storable()))
77
+ end
78
+
79
+ @scan.putBackToken()
80
+
81
+ return e
82
+ end
83
+
84
+ def Storable()
85
+ result = Factor()
86
+
87
+ t = @scan.getToken()
88
+
89
+ if t.type == :keyword then
90
+ if t.lex == "S" then
91
+ return StoreNode.new(result)
92
+ end
93
+ puts "Expected S found: " + t.lex
94
+ raise ParseError.new
95
+ end
96
+
97
+ @scan.putBackToken()
98
+
99
+ return result
100
+
101
+ end
102
+
103
+ def Factor()
104
+ t = @scan.getToken()
105
+
106
+ if t.type == :number then
107
+ return NumNode.new(t.lex.to_i)
108
+ end
109
+
110
+ if t.type == :keyword then
111
+ if t.lex == "R" then
112
+ return RecallNode.new
113
+ end
114
+
115
+ puts "Expected R found: " + t.lex
116
+ end
117
+
118
+ if t.type == :lparen then
119
+ result = Expr()
120
+
121
+ t = @scan.getToken()
122
+
123
+ if t.type == :rparen then
124
+ return result
125
+ end
126
+
127
+ puts "Expected ) found: " + t.type.to_s
128
+ raise ParseError.new
129
+ end
130
+
131
+
132
+ return e
133
+
134
+ puts "Expected number, R, ( found: " + t.type.to_s
135
+ raise ParseError.new
136
+
137
+ end
138
+ end
data/lib/scanner.rb ADDED
@@ -0,0 +1,128 @@
1
+ require 'stringio'
2
+ require 'calcex'
3
+
4
+
5
+ class Scanner
6
+ def initialize(inStream)
7
+ @istream = inStream
8
+ @keywords = Set.new(["S","R"])
9
+ @lineCount = 1
10
+ @colCount = -1
11
+ @needToken = true
12
+ @lastToken = nil
13
+ end
14
+
15
+ def putBackToken
16
+ @needToken = false
17
+ end
18
+
19
+ def getToken
20
+ unless @needToken
21
+ @needToken = true
22
+ return @lastToken
23
+ end
24
+
25
+ state = 0
26
+ foundOne = false
27
+ c = @istream.getc()
28
+
29
+ if @istream.eof() then
30
+ @lastToken = Token.new(:eof,@lineCount,@colCount)
31
+ return @lastToken
32
+ end
33
+
34
+ until foundOne
35
+ @colCount = @colCount + 1
36
+ case state
37
+ when 0
38
+ lex = ""
39
+ column = @colCount
40
+ line = @lineCount
41
+ if isLetter(c) then state=1
42
+ elsif isDigit(c) then state=2
43
+ elsif c == ?+ then state = 3
44
+ elsif c == ?- then state = 4
45
+ elsif c == ?* then state = 5
46
+ elsif c == ?/ then state = 6
47
+ elsif c == ?( then state = 7
48
+ elsif c == ?) then state = 8
49
+ elsif c == ?\n then
50
+ @colCount = -1
51
+ @lineCount = @lineCount+1
52
+ elsif isWhiteSpace(c) then state = state #ignore whitespace
53
+ elsif @istream.eof() then
54
+ @foundOne = true
55
+ type = :eof
56
+ else
57
+ puts "Unrecognized Token found at line ",line," and column ",column,"\n"
58
+ raise UnrecognizedTokenException # "Unrecognized Token"
59
+ end
60
+ when 1
61
+ if isLetter(c) or isDigit(c) then state = 1
62
+ else
63
+ if @keywords.include?(lex) then
64
+ foundOne = true
65
+ type = :keyword
66
+ else
67
+ foundOne = true
68
+ type = :identifier
69
+ end
70
+ end
71
+ when 2
72
+ if isDigit(c) then state = 2
73
+ else
74
+ type = :number
75
+ foundOne = true
76
+ end
77
+ when 3
78
+ type = :add
79
+ foundOne = true
80
+ when 4
81
+ type = :sub
82
+ foundOne = true
83
+ when 5
84
+ type = :times
85
+ foundOne = true
86
+ when 6
87
+ type = :divide
88
+ foundOne = true
89
+ when 7
90
+ type = :lparen
91
+ foundOne = true
92
+ when 8
93
+ type = :rparen
94
+ foundOne = true
95
+ end
96
+
97
+ if !foundOne then
98
+ lex.concat(c)
99
+ c = @istream.getc()
100
+ end
101
+
102
+ end
103
+
104
+ @istream.ungetc(c)
105
+ @colCount = @colCount - 1
106
+ if type == :number or type == :identifier or type == :keyword then
107
+ t = LexicalToken.new(type,lex,line,column)
108
+ else
109
+ t = Token.new(type,line,column)
110
+ end
111
+
112
+ @lastToken = t
113
+ return t
114
+ end
115
+
116
+ private
117
+ def isLetter(c)
118
+ return ((?a <= c and c <= ?z) or (?A <= c and c <= ?Z))
119
+ end
120
+
121
+ def isDigit(c)
122
+ return (?0 <= c and c <= ?9)
123
+ end
124
+
125
+ def isWhiteSpace(c)
126
+ return (c == ?\ or c == ?\n or c == ?\t)
127
+ end
128
+ end
data/lib/token.rb ADDED
@@ -0,0 +1,19 @@
1
+ class Token
2
+ attr_reader :type, :line, :col
3
+
4
+ def initialize(type,lineNum,colNum)
5
+ @type = type
6
+ @line = lineNum
7
+ @col = colNum
8
+ end
9
+ end
10
+
11
+ class LexicalToken < Token #herencia simple token
12
+ attr_reader :lex
13
+
14
+ def initialize(type,lex,lineNum,colNum) #lexema que va a leer polimorfismo
15
+ super(type,lineNum,colNum) #clase padre token
16
+
17
+ @lex = lex #instancias de lexical token podran tener @lex
18
+ end
19
+ end
metadata ADDED
@@ -0,0 +1,51 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: calc_dmoral12
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.2
5
+ platform: ruby
6
+ authors:
7
+ - Kent D. Lee - Juan Francisco Cardona Mc-juan camilo gomez
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2015-11-12 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: An calculator implementation on ruby
14
+ email: fcardona@eafit.edu.co-jgomez88@eafit.edu.co
15
+ executables:
16
+ - calc
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - bin/calc
21
+ - lib/ast.rb
22
+ - lib/calcex.rb
23
+ - lib/calculator.rb
24
+ - lib/parser.rb
25
+ - lib/scanner.rb
26
+ - lib/token.rb
27
+ homepage: http://www1.eafit.edu.co/fcardona/cursos/st0244/rubycal
28
+ licenses:
29
+ - ARTISTIC
30
+ metadata: {}
31
+ post_install_message:
32
+ rdoc_options: []
33
+ require_paths:
34
+ - lib
35
+ required_ruby_version: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - ">="
38
+ - !ruby/object:Gem::Version
39
+ version: '0'
40
+ required_rubygems_version: !ruby/object:Gem::Requirement
41
+ requirements:
42
+ - - ">="
43
+ - !ruby/object:Gem::Version
44
+ version: '0'
45
+ requirements: []
46
+ rubyforge_project:
47
+ rubygems_version: 2.4.7
48
+ signing_key:
49
+ specification_version: 4
50
+ summary: Another calculator in ruby
51
+ test_files: []