rus3 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: a733b3f40b0fb9223d58d5293f08f68cbc404dbea10df196e92d15e47453a9b6
4
+ data.tar.gz: 20749c1d7410e925577b76fdca4ecf92ffc0c1ff4aef5d894079548c324f84ed
5
+ SHA512:
6
+ metadata.gz: 5350b2341a176d7844910acb888faeae61c499659471148c9370deaad7ba2192e346a5d7e8a03cc3799540c2fe372feabc925cb8f8bdfd94e34dcaad01a36247
7
+ data.tar.gz: 2aab5a0555331938bc986d418dcb18e0d116be078088846bdad73aebc520ae8bda7b1b334f5ec26dc78bfb5ffe814ff380d1fc9eb9072ad027f4b8539f4fb3ed
@@ -0,0 +1,18 @@
1
+ name: Build
2
+
3
+ on: [push,pull_request]
4
+
5
+ jobs:
6
+ build:
7
+ runs-on: ubuntu-latest
8
+ steps:
9
+ - uses: actions/checkout@v2
10
+ - name: Set up Ruby
11
+ uses: ruby/setup-ruby@v1
12
+ with:
13
+ ruby-version: 3.0.0
14
+ - name: Run the default task
15
+ run: |
16
+ gem install bundler -v 2.2.3
17
+ bundle install
18
+ bundle exec rake
data/.gitignore ADDED
@@ -0,0 +1,56 @@
1
+ *.gem
2
+ *.rbc
3
+ /.config
4
+ /coverage/
5
+ /InstalledFiles
6
+ /pkg/
7
+ /spec/reports/
8
+ /spec/examples.txt
9
+ /test/tmp/
10
+ /test/version_tmp/
11
+ /tmp/
12
+
13
+ # Used by dotenv library to load environment variables.
14
+ # .env
15
+
16
+ # Ignore Byebug command history file.
17
+ .byebug_history
18
+
19
+ ## Specific to RubyMotion:
20
+ .dat*
21
+ .repl_history
22
+ build/
23
+ *.bridgesupport
24
+ build-iPhoneOS/
25
+ build-iPhoneSimulator/
26
+
27
+ ## Specific to RubyMotion (use of CocoaPods):
28
+ #
29
+ # We recommend against adding the Pods directory to your .gitignore. However
30
+ # you should judge for yourself, the pros and cons are mentioned at:
31
+ # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control
32
+ #
33
+ # vendor/Pods/
34
+
35
+ ## Documentation cache and generated files:
36
+ /.yardoc/
37
+ /_yardoc/
38
+ /doc/
39
+ /rdoc/
40
+
41
+ ## Environment normalization:
42
+ /.bundle/
43
+ /vendor/bundle
44
+ /lib/bundler/man/
45
+
46
+ # for a library or gem, you might want to ignore these files since the code is
47
+ # intended to run in multiple environments; otherwise, check them in:
48
+ # Gemfile.lock
49
+ # .ruby-version
50
+ # .ruby-gemset
51
+
52
+ # unless supporting rvm < 1.11.0 or doing something fancy, ignore this:
53
+ .rvmrc
54
+
55
+ # Used by RuboCop. Remote config files pulled in from inherit_from directive.
56
+ # .rubocop-https?--*
data/CHANGELOG.md ADDED
@@ -0,0 +1,14 @@
1
+ # Change Log
2
+ All notable changes to this project will be documented in this file.
3
+
4
+ The format is based on [Keep a Changelog](https://keepachangelog.com/)
5
+ and this project adheres to [Semantic Versioning](https://semver.org/).
6
+
7
+ ## [Unreleased]
8
+ - Add `CHANGELOG.md`. (2021-04-04)
9
+ - Modify some files to pass tests. (2021-04-04)
10
+ - Add files those are generated by `bundler`. (2021-04-04)
11
+
12
+ ## [0.1.0] - 2021-04-21
13
+ - Initial release:
14
+ - Rus3 can translate fundamental syntax of Scheme into Ruby.
data/Gemfile ADDED
@@ -0,0 +1,10 @@
1
+ # frozen_string_literal: true
2
+
3
+ source "https://rubygems.org"
4
+
5
+ # Specify your gem's dependencies in rus3.gemspec
6
+ gemspec
7
+
8
+ gem "rake", "~> 13.0"
9
+
10
+ gem "minitest", "~> 5.0"
data/Gemfile.lock ADDED
@@ -0,0 +1,21 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ rus3 (0.1.0)
5
+
6
+ GEM
7
+ remote: https://rubygems.org/
8
+ specs:
9
+ minitest (5.14.4)
10
+ rake (13.0.3)
11
+
12
+ PLATFORMS
13
+ x86_64-darwin-20
14
+
15
+ DEPENDENCIES
16
+ minitest (~> 5.0)
17
+ rake (~> 13.0)
18
+ rus3!
19
+
20
+ BUNDLED WITH
21
+ 2.2.15
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2021 mnbi
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,182 @@
1
+ # Rus^3
2
+
3
+ [![Build Status](https://github.com/mnbi/rus3/workflows/Build/badge.svg)](https://github.com/mnbi/rus3/actions?query=workflow%3A"Build")
4
+
5
+ Ruby with Syntax Sugar of Scheme.
6
+ Or a simple translator from Scheme program to Ruby.
7
+
8
+ ## Installation
9
+
10
+ Execute as:
11
+
12
+ > gem install rus3
13
+
14
+ ## Usage
15
+
16
+ You can start the Rus3 REPL with the command, `rus3`.
17
+
18
+ ``` scheme
19
+ > rus3
20
+ A simple REPL for Rus3:
21
+ - Rus3 version: 0.1.0
22
+ - REPL version: 0.1.0
23
+ - Parser version 0.1.0 ((scheme-parser-version . 0.1.0) (scheme-lexer-version . 0.1.0))
24
+ - Evaluator version: 0.1.0
25
+ - using built-in PRINTER
26
+ Rus3(scheme)>
27
+ ```
28
+
29
+ `Rus3(scheme)>` is the prompt of the Rus3.
30
+
31
+ In the REPL, you can enter Scheme expressions. The REPL reads your
32
+ Scheme expressions, translates it to Ruby expressions, and
33
+ evaluated them. Then, the REPL prints the result after `==> `.
34
+
35
+ ### Literal of Scheme values
36
+
37
+ Boolean (`#f` and `#t`), an empty list (`()`), a string, and numbers
38
+ (integer, real, rational and complex) can be translated.
39
+
40
+ ``` scheme
41
+ Rus3(scheme)> #f
42
+ ==> false
43
+ Rus3(scheme)> #t
44
+ ==> true
45
+ Rus3(scheme)> ()
46
+ ==> []
47
+ Rus3(scheme)> "foo"
48
+ ==> "foo"
49
+ Rus3(scheme)> 123.456
50
+ ==> 123.456
51
+ Rus3(scheme)> 1/9
52
+ ==> (1/9)
53
+ Rus3(scheme)> 3+4i
54
+ ==> (3+4i)
55
+ ```
56
+
57
+ ### Procedure call
58
+
59
+ You can apply a defined procedure.
60
+
61
+ ``` scheme
62
+ Rus3(scheme)> (list 1 2 3)
63
+ ==> [1, 2, 3]
64
+ Rus3(scheme)> (append (list 1 2 3) (list 4 5 6))
65
+ ==> [1, 2, 3, 4, 5, 6]
66
+ ```
67
+
68
+ ### Lambda expression
69
+
70
+ You can apply lambda expression as a procedure.
71
+
72
+ ``` scheme
73
+ Rus3(scheme)> ((lambda (x) (* x x)) 2)
74
+ ==> 4
75
+ ```
76
+
77
+ ### Conditional expression
78
+
79
+ ``` scheme
80
+ Rus3(scheme)> (if (< 2 3) "true" "false")
81
+ ==> "true"
82
+ ```
83
+
84
+ `cond` type is also available.
85
+
86
+ ### Assignment
87
+
88
+ ``` scheme
89
+ Rus3(scheme)> (set! x 2)
90
+ ==> 2
91
+ Rus3(scheme)> x
92
+ ==> 2
93
+ ```
94
+
95
+ ### Define a procedure
96
+
97
+ ``` scheme
98
+ Rus3(scheme)> (define (fact n) (if (= n 0) 1 (* n (fact (- n 1)))))
99
+ ==> :fact
100
+ Rus3(scheme)> (fact 5)
101
+ ==> 120
102
+ ```
103
+
104
+ ### Let expression
105
+
106
+ ``` scheme
107
+ Rus3(scheme)> (let ((x 2) (y 3)) (* x y))
108
+ ==> 6
109
+ ```
110
+
111
+ ## Procedures in the Scheme specification (R5RS or R7RS-small)
112
+
113
+ Following procedures described in the spec is available.
114
+
115
+ - Predicates:
116
+ - null?, list?
117
+ - eqv?, eq?
118
+ - boolean?, pair?, symbol?, number?, string?
119
+ - char?, vector?, and port? are defined but it always returns `false`.
120
+ - complex?, real?, rational?, integer?
121
+ - zero?, positive?, negative?, odd?, even?
122
+ - string-eq?, string-ci-eq?, string-lt?, string-gt?, string-le?,
123
+ string-ge?, string-ci-lt?, string-ci-gt?, string-ci-le?, string-ci-ge?
124
+ - some predicates for `char` and `port` are defined but it always
125
+ returns `false`.
126
+
127
+ - List operations
128
+ - cons, car, cdr, set-car!, set-cdr!, cxxr (caar and so on)
129
+ - list, length, append, reverse, list-tail, list-ref
130
+
131
+ - Write values
132
+ - write
133
+ - display
134
+
135
+ - Control features
136
+ - map
137
+ - zip
138
+
139
+ ## System interface
140
+
141
+ ### Load-scm procedure
142
+
143
+ Reads a Scheme program file, then translates and evaluates.
144
+
145
+ ``` scheme
146
+ Rus3(scheme)> (load-scm "examples/iota.scm")
147
+ (1 2 3 4 5 6 7 8 9 10)
148
+ (1/9 2/9 1/3 4/9 5/9 2/3 7/9 8/9 1/1 10/9)
149
+ ==> #<Rus3::Undef:0x00007f90f8945418>
150
+ ```
151
+
152
+ ## Restrictions
153
+
154
+ In the current version, there are several restrictions, those are
155
+ deviations from the Scheme specification (R5RS or R7RS-small).
156
+
157
+ - `Equal?` does not defined. Since `Object#equal?` must not re-define
158
+ in Ruby.
159
+ - `Cdr` and `list-tail` do not return a reference of the part of the
160
+ target list. They return a new list structure which contains the
161
+ same member of the target list.
162
+ - Rus3 would replace some character which can not use as a part of
163
+ identifier in Ruby. So, it is possible that some collision of
164
+ identifiers.
165
+ - Nested definition of procedure can use outside.
166
+
167
+ Some of these may be disappeared in the future version, or may not be.
168
+
169
+ ## Development
170
+
171
+ After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
172
+
173
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
174
+
175
+ ## Contributing
176
+
177
+ Bug reports and pull requests are welcome on GitHub at [https://github.com/mnbi/rus3](https://github.com/mnbi/rus3).
178
+
179
+
180
+ ## License
181
+
182
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler/gem_tasks"
4
+ require "rake/testtask"
5
+
6
+ Rake::TestTask.new(:test) do |t|
7
+ t.libs << "test"
8
+ t.libs << "lib"
9
+ t.test_files = FileList["test/**/*_test.rb"]
10
+ end
11
+
12
+ task default: :test
13
+
14
+ require "rdoc/task"
15
+
16
+ RDoc::Task.new do |rdoc|
17
+ rdoc.generator = "ri"
18
+ rdoc.rdoc_dir = "rdoc"
19
+ rdoc.rdoc_files.include("lib/**/*.rb")
20
+ end
data/bin/console ADDED
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require "bundler/setup"
5
+
6
+ require "rus3"
7
+
8
+ # You can add fixtures and/or initialization code here to make experimenting
9
+ # with your gem easier. You can also use a different console, if you like.
10
+
11
+ # (If you use this, don't forget to add pry to your Gemfile!)
12
+ # require "pry"
13
+ # Pry.start
14
+
15
+ require "irb"
16
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
data/examples/fact.scm ADDED
@@ -0,0 +1,10 @@
1
+ (define (fact n)
2
+ (define (fact-iter n r c)
3
+ (if (< n c)
4
+ r
5
+ (fact-iter n (* r c) (+ c 1))))
6
+ (fact-iter n 1 1))
7
+
8
+ (display (fact 10))
9
+ (display (fact 100))
10
+ (display (fact 1000))
data/examples/fib.scm ADDED
@@ -0,0 +1,9 @@
1
+ (define (fib-iter n f0 f1)
2
+ (cond ((= n 0) f0)
3
+ ((= n 1) f1)
4
+ (else (fib-iter (- n 1) f1 (+ f0 f1)))))
5
+
6
+ (define (fib n)
7
+ (fib-iter n 0 1))
8
+
9
+ (fib 100)
data/examples/iota.scm ADDED
@@ -0,0 +1,13 @@
1
+ (define (iota-iter result count start step)
2
+ (if (zero? count)
3
+ result
4
+ (iota-iter (append result (list start))
5
+ (- count 1)
6
+ (+ start step)
7
+ step)))
8
+
9
+ (define (iota count start step)
10
+ (iota-iter () count start step))
11
+
12
+ (display (iota 10 1 1))
13
+ (display (iota 10 1/9 11/99))
data/exe/rus3 ADDED
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "rus3"
4
+
5
+ Rus3::Repl.start(verbose: ARGV.size > 0)
data/lib/rus3.rb ADDED
@@ -0,0 +1,52 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Rus3
4
+
5
+ # An empty list is a special object in Scheme language. The role
6
+ # roughly corresponds to the one of 'nil' in Ruby.
7
+
8
+ module EmptyList
9
+
10
+ # Represents an empty list.
11
+ EMPTY_LIST = []
12
+
13
+ # Returns true if the argument is an empty list. RuS^3 treats nil
14
+ # (an instance of NilClass) as an empty list.
15
+
16
+ def null?(obj)
17
+ obj.instance_of?(Array) and obj.empty?
18
+ end
19
+
20
+ end
21
+
22
+ # Indicates the values is not specified in the Scheme specification.
23
+ # This value is intended using to be returned from procedures those
24
+ # does not have any specified value as its return value.
25
+
26
+ require "singleton"
27
+ class Undef
28
+ include Singleton
29
+
30
+ def to_s
31
+ "\#<undef>"
32
+ end
33
+ end
34
+ UNDEF = Undef.instance
35
+
36
+ require_relative "rus3/version"
37
+ require_relative "rus3/error"
38
+
39
+ require_relative "rus3/pair"
40
+ require_relative "rus3/char"
41
+ require_relative "rus3/port"
42
+
43
+ require_relative "rus3/procedure/predicate"
44
+ require_relative "rus3/procedure/list"
45
+ require_relative "rus3/procedure/control"
46
+ require_relative "rus3/procedure/write"
47
+
48
+ require_relative "rus3/parser"
49
+ require_relative "rus3/evaluator"
50
+ require_relative "rus3/printer"
51
+ require_relative "rus3/repl"
52
+ end