Mowkow 0.1.0__tar.gz

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.
@@ -0,0 +1,117 @@
1
+ Metadata-Version: 2.4
2
+ Name: Mowkow
3
+ Version: 0.1.0
4
+ Summary: Mowkow: A Korean LISP Interpreter
5
+ Author-email: Gyun Woo <woogyun@pnu.edu>
6
+ Keywords: Korean,LISP,coding,programming,interpreter
7
+ Requires-Python: >=3.10
8
+ Description-Content-Type: text/markdown
9
+
10
+ # mowkow
11
+ 머꼬: 한글 LISP
12
+
13
+ ## 실행 방법
14
+ Python 3.10 이상을 설치한 후 다음 명령을 수행합니다.
15
+ ```
16
+ python main.py
17
+ ```
18
+ Windows 운영체제에서는 dist의 mk.exe를 다운로드하셔서 명령 프롬프트에서 다음과 같이 수행합니다.
19
+ ```
20
+ mk.exe
21
+ ```
22
+
23
+ 종료하려면 그냥 엔터를 입력하면 됩니다.
24
+
25
+ ## 테스트 입력
26
+
27
+ 다음 입력을 수행해 보세요.
28
+
29
+ ```
30
+ > (+ 10 20)
31
+ 30
32
+ > (그대로 10)
33
+ 10
34
+ > (그대로 (+ 10 20))
35
+ 30
36
+ > (그대로 '(+ 10 20))
37
+ (+ 10 20)
38
+ > (절댓값 (- 20))
39
+ 오류: <내장함수 '-'>: 인수 개수 오류입니다.
40
+ > (절댓값 (- 0 20))
41
+ 20
42
+ > (머 '(1 2 3))
43
+ 1
44
+ > (꼬 '(1 2 3))
45
+ (2 3)
46
+ > (잠시 ((이 2) (삼 3)) (+ 이 삼))
47
+ 5
48
+ > (정의 (합 수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1)))))
49
+ > (합 4)
50
+ 10
51
+ > (정의 합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))
52
+ > (합 5)
53
+ 15
54
+ > (잠시 ((인수 5) (합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))) (합 인수))
55
+ 15
56
+ ```
57
+
58
+ ## 테스트 프로그램
59
+ 두 양수를 입력받아 최대공약수와 최소공배수를 구하는 프로그램(`gcd_lcm.mk`)의 예를 보면 다음과 같습니다.
60
+ ```
61
+ (정의 (나머지 가 나)
62
+ (- 가 (* (/ 가 나) 나)))
63
+
64
+ (정의 (최대공약수 가 나)
65
+ (만약 (= 나 0)
66
+ 가
67
+ (최대공약수 나 (나머지 가 나))))
68
+
69
+ (정의 (최소공배수 가 나)
70
+ (/ (* 가 나) (최대공약수 가 나)))
71
+
72
+ (정의 가 (읽기))
73
+ (정의 나 (읽기))
74
+ (쓰기 (최대공약수 가 나))
75
+ (쓰기 (최소공배수 가 나))
76
+ ```
77
+ 위 프로그램은 다음과 같이 수행할 수 있습니다.
78
+ ```
79
+ > python main.py gcd_lcm.mk
80
+ ```
81
+
82
+
83
+ ## 테스트 코드
84
+
85
+ 테스트 코드 폴더의 테스트 파일 source.mk를 수행하려면 다음과 같이 수행하시면 됩니다.
86
+
87
+ ```
88
+ python main.py test_code/source.mk
89
+ ```
90
+
91
+ 윈도우 실행 파일 mk.exe로 수행하시려면 다음과 같이 수행하시면 됩니다.
92
+ ```
93
+ mk.exe test_code/source.mk
94
+ ```
95
+
96
+ ## Windows용 배치 파일
97
+
98
+ 머꼬 프로그램 파일은 UTF-8 인코딩으로 작성해야 합니다.
99
+ `test_code`의 예제 프로그램도 그렇게 작성된 것입니다.
100
+ 이를 Windows의 명령 프롬프트(`cmd`) 창에서 보려면 문자 인코딩을 UTF-8 인코딩으로 바꾸어야 합니다.
101
+ 이때 다음 명령어를 사용하실 수 있습니다.
102
+
103
+ ```
104
+ gomk
105
+ ```
106
+
107
+ 다시 원래 인코딩(code page 949, EUC-KR 호환)으로 명령 프롬프트를 회복하시려면 다음 명령어를 사용하시기 바랍니다.
108
+
109
+ ```
110
+ kmog
111
+ ```
112
+
113
+ ## Authors
114
+
115
+ * **우균(Gyun Woo)** - *최초 작업* - [Gyun Woo](https://github.com/woogyun)
116
+
117
+
@@ -0,0 +1,14 @@
1
+ README.md
2
+ pyproject.toml
3
+ Mowkow.egg-info/PKG-INFO
4
+ Mowkow.egg-info/SOURCES.txt
5
+ Mowkow.egg-info/dependency_links.txt
6
+ Mowkow.egg-info/entry_points.txt
7
+ Mowkow.egg-info/top_level.txt
8
+ mowkow/__init__.py
9
+ mowkow/_data.py
10
+ mowkow/_error.py
11
+ mowkow/_eval.py
12
+ mowkow/_parse.py
13
+ mowkow/library_kor.scm
14
+ mowkow/main.py
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ mk = mowkow.main:main
@@ -0,0 +1 @@
1
+ mowkow
mowkow-0.1.0/PKG-INFO ADDED
@@ -0,0 +1,117 @@
1
+ Metadata-Version: 2.4
2
+ Name: Mowkow
3
+ Version: 0.1.0
4
+ Summary: Mowkow: A Korean LISP Interpreter
5
+ Author-email: Gyun Woo <woogyun@pnu.edu>
6
+ Keywords: Korean,LISP,coding,programming,interpreter
7
+ Requires-Python: >=3.10
8
+ Description-Content-Type: text/markdown
9
+
10
+ # mowkow
11
+ 머꼬: 한글 LISP
12
+
13
+ ## 실행 방법
14
+ Python 3.10 이상을 설치한 후 다음 명령을 수행합니다.
15
+ ```
16
+ python main.py
17
+ ```
18
+ Windows 운영체제에서는 dist의 mk.exe를 다운로드하셔서 명령 프롬프트에서 다음과 같이 수행합니다.
19
+ ```
20
+ mk.exe
21
+ ```
22
+
23
+ 종료하려면 그냥 엔터를 입력하면 됩니다.
24
+
25
+ ## 테스트 입력
26
+
27
+ 다음 입력을 수행해 보세요.
28
+
29
+ ```
30
+ > (+ 10 20)
31
+ 30
32
+ > (그대로 10)
33
+ 10
34
+ > (그대로 (+ 10 20))
35
+ 30
36
+ > (그대로 '(+ 10 20))
37
+ (+ 10 20)
38
+ > (절댓값 (- 20))
39
+ 오류: <내장함수 '-'>: 인수 개수 오류입니다.
40
+ > (절댓값 (- 0 20))
41
+ 20
42
+ > (머 '(1 2 3))
43
+ 1
44
+ > (꼬 '(1 2 3))
45
+ (2 3)
46
+ > (잠시 ((이 2) (삼 3)) (+ 이 삼))
47
+ 5
48
+ > (정의 (합 수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1)))))
49
+ > (합 4)
50
+ 10
51
+ > (정의 합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))
52
+ > (합 5)
53
+ 15
54
+ > (잠시 ((인수 5) (합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))) (합 인수))
55
+ 15
56
+ ```
57
+
58
+ ## 테스트 프로그램
59
+ 두 양수를 입력받아 최대공약수와 최소공배수를 구하는 프로그램(`gcd_lcm.mk`)의 예를 보면 다음과 같습니다.
60
+ ```
61
+ (정의 (나머지 가 나)
62
+ (- 가 (* (/ 가 나) 나)))
63
+
64
+ (정의 (최대공약수 가 나)
65
+ (만약 (= 나 0)
66
+ 가
67
+ (최대공약수 나 (나머지 가 나))))
68
+
69
+ (정의 (최소공배수 가 나)
70
+ (/ (* 가 나) (최대공약수 가 나)))
71
+
72
+ (정의 가 (읽기))
73
+ (정의 나 (읽기))
74
+ (쓰기 (최대공약수 가 나))
75
+ (쓰기 (최소공배수 가 나))
76
+ ```
77
+ 위 프로그램은 다음과 같이 수행할 수 있습니다.
78
+ ```
79
+ > python main.py gcd_lcm.mk
80
+ ```
81
+
82
+
83
+ ## 테스트 코드
84
+
85
+ 테스트 코드 폴더의 테스트 파일 source.mk를 수행하려면 다음과 같이 수행하시면 됩니다.
86
+
87
+ ```
88
+ python main.py test_code/source.mk
89
+ ```
90
+
91
+ 윈도우 실행 파일 mk.exe로 수행하시려면 다음과 같이 수행하시면 됩니다.
92
+ ```
93
+ mk.exe test_code/source.mk
94
+ ```
95
+
96
+ ## Windows용 배치 파일
97
+
98
+ 머꼬 프로그램 파일은 UTF-8 인코딩으로 작성해야 합니다.
99
+ `test_code`의 예제 프로그램도 그렇게 작성된 것입니다.
100
+ 이를 Windows의 명령 프롬프트(`cmd`) 창에서 보려면 문자 인코딩을 UTF-8 인코딩으로 바꾸어야 합니다.
101
+ 이때 다음 명령어를 사용하실 수 있습니다.
102
+
103
+ ```
104
+ gomk
105
+ ```
106
+
107
+ 다시 원래 인코딩(code page 949, EUC-KR 호환)으로 명령 프롬프트를 회복하시려면 다음 명령어를 사용하시기 바랍니다.
108
+
109
+ ```
110
+ kmog
111
+ ```
112
+
113
+ ## Authors
114
+
115
+ * **우균(Gyun Woo)** - *최초 작업* - [Gyun Woo](https://github.com/woogyun)
116
+
117
+
mowkow-0.1.0/README.md ADDED
@@ -0,0 +1,108 @@
1
+ # mowkow
2
+ 머꼬: 한글 LISP
3
+
4
+ ## 실행 방법
5
+ Python 3.10 이상을 설치한 후 다음 명령을 수행합니다.
6
+ ```
7
+ python main.py
8
+ ```
9
+ Windows 운영체제에서는 dist의 mk.exe를 다운로드하셔서 명령 프롬프트에서 다음과 같이 수행합니다.
10
+ ```
11
+ mk.exe
12
+ ```
13
+
14
+ 종료하려면 그냥 엔터를 입력하면 됩니다.
15
+
16
+ ## 테스트 입력
17
+
18
+ 다음 입력을 수행해 보세요.
19
+
20
+ ```
21
+ > (+ 10 20)
22
+ 30
23
+ > (그대로 10)
24
+ 10
25
+ > (그대로 (+ 10 20))
26
+ 30
27
+ > (그대로 '(+ 10 20))
28
+ (+ 10 20)
29
+ > (절댓값 (- 20))
30
+ 오류: <내장함수 '-'>: 인수 개수 오류입니다.
31
+ > (절댓값 (- 0 20))
32
+ 20
33
+ > (머 '(1 2 3))
34
+ 1
35
+ > (꼬 '(1 2 3))
36
+ (2 3)
37
+ > (잠시 ((이 2) (삼 3)) (+ 이 삼))
38
+ 5
39
+ > (정의 (합 수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1)))))
40
+ > (합 4)
41
+ 10
42
+ > (정의 합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))
43
+ > (합 5)
44
+ 15
45
+ > (잠시 ((인수 5) (합 (람다 (수) (만약 (= 수 0) 0 (+ 수 (합 (- 수 1))))))) (합 인수))
46
+ 15
47
+ ```
48
+
49
+ ## 테스트 프로그램
50
+ 두 양수를 입력받아 최대공약수와 최소공배수를 구하는 프로그램(`gcd_lcm.mk`)의 예를 보면 다음과 같습니다.
51
+ ```
52
+ (정의 (나머지 가 나)
53
+ (- 가 (* (/ 가 나) 나)))
54
+
55
+ (정의 (최대공약수 가 나)
56
+ (만약 (= 나 0)
57
+ 가
58
+ (최대공약수 나 (나머지 가 나))))
59
+
60
+ (정의 (최소공배수 가 나)
61
+ (/ (* 가 나) (최대공약수 가 나)))
62
+
63
+ (정의 가 (읽기))
64
+ (정의 나 (읽기))
65
+ (쓰기 (최대공약수 가 나))
66
+ (쓰기 (최소공배수 가 나))
67
+ ```
68
+ 위 프로그램은 다음과 같이 수행할 수 있습니다.
69
+ ```
70
+ > python main.py gcd_lcm.mk
71
+ ```
72
+
73
+
74
+ ## 테스트 코드
75
+
76
+ 테스트 코드 폴더의 테스트 파일 source.mk를 수행하려면 다음과 같이 수행하시면 됩니다.
77
+
78
+ ```
79
+ python main.py test_code/source.mk
80
+ ```
81
+
82
+ 윈도우 실행 파일 mk.exe로 수행하시려면 다음과 같이 수행하시면 됩니다.
83
+ ```
84
+ mk.exe test_code/source.mk
85
+ ```
86
+
87
+ ## Windows용 배치 파일
88
+
89
+ 머꼬 프로그램 파일은 UTF-8 인코딩으로 작성해야 합니다.
90
+ `test_code`의 예제 프로그램도 그렇게 작성된 것입니다.
91
+ 이를 Windows의 명령 프롬프트(`cmd`) 창에서 보려면 문자 인코딩을 UTF-8 인코딩으로 바꾸어야 합니다.
92
+ 이때 다음 명령어를 사용하실 수 있습니다.
93
+
94
+ ```
95
+ gomk
96
+ ```
97
+
98
+ 다시 원래 인코딩(code page 949, EUC-KR 호환)으로 명령 프롬프트를 회복하시려면 다음 명령어를 사용하시기 바랍니다.
99
+
100
+ ```
101
+ kmog
102
+ ```
103
+
104
+ ## Authors
105
+
106
+ * **우균(Gyun Woo)** - *최초 작업* - [Gyun Woo](https://github.com/woogyun)
107
+
108
+
File without changes
@@ -0,0 +1,248 @@
1
+ #coding: utf-8
2
+
3
+ # Ph 4(eval): Pair.car() and Pair.cdr()
4
+ # global car(Data) and cdr(Data)
5
+ # Symbol.value(self)
6
+ # global islist(Data): recursive
7
+ # Data.issymbol(), Data.isint(), Symbol.issymbol(), Int.isint()
8
+ # islist(Data)
9
+ # bug: Pair의 함수 이름과 필드 이름을 똑같이 car, cdr로 설정했었음.
10
+ # -> 필드를 _car, _cdr로 바꿈
11
+
12
+ # Ph 5(car): class Builtin
13
+ # global mkbuiltin, cplist
14
+ # Pair.setcar(Data)
15
+ # Integer.value()
16
+
17
+ # Ph 7(clo): class Closure
18
+ # Data.isclosure()
19
+ # global allsymbols(Data)
20
+ # from _error import *
21
+
22
+ # Ph 10(var): Closure.__init__ does not use allsymbols
23
+ # but checks the parameter types manually
24
+
25
+ # Ph 11(macro): Macro(Data) class is a copycat of Closure(Data)
26
+ # Macro.isclosure()를 Macro.ismacro()로 대체
27
+ # Data.ismacro() 추가
28
+ # Macro 생성자를 호출하는 전역 함수 mkmacro 추가
29
+
30
+ from ._error import ErrType, ErrSyntax
31
+
32
+ class Data:
33
+ """클래스 Data는 머꼬의 모든 데이터 클래스의 부모 클래스입니다."""
34
+ def __init__(self):
35
+ """Data 클래스는 추상 클래스이므로 비워 두었습니다."""
36
+ def ispair(self) -> bool:
37
+ """짝(pair)인지 점검하는 함수. 짝이면 참"""
38
+ return False
39
+ def isnil(self) -> bool:
40
+ """공(nil)인지 점검하는 함수. 공이면 참"""
41
+ return False
42
+ def issymbol(self) -> bool:
43
+ return False
44
+ def isint(self) -> bool:
45
+ return False
46
+ def isstr(self) -> bool:
47
+ return False
48
+ def isbuiltin(self) -> bool:
49
+ return False
50
+ def isclosure(self) -> bool:
51
+ return False
52
+ def ismacro(self) -> bool:
53
+ return False
54
+ def value(self) -> None:
55
+ """ place holder for value """
56
+ return None
57
+ def car(self) -> None:
58
+ """place holder for car"""
59
+ return None
60
+ def cdr(self) -> None:
61
+ """place holder for cdr"""
62
+ return None
63
+
64
+ class Nil(Data):
65
+ def __init__(self):
66
+ pass
67
+ def __str__(self):
68
+ return "공"
69
+ def isnil(self) -> bool:
70
+ return True
71
+
72
+ class Pair(Data):
73
+ def __init__(self, car_val: Data, cdr_val: Data):
74
+ self._car, self._cdr = car_val, cdr_val
75
+ def ispair(self) -> bool:
76
+ return True
77
+ def __str__(self) -> str:
78
+ rval = f"({self._car}"
79
+ tail = self._cdr
80
+ while not tail.isnil():
81
+ if tail.ispair(): # Bug230111: self.cdr.ispair() -> tail.ispair()
82
+ rval += f" {tail._car}" # type: ignore
83
+ tail = tail._cdr # type: ignore
84
+ else:
85
+ rval += f" . {tail}"
86
+ break # break가 꼭 필요함
87
+ rval += ")"
88
+ return rval
89
+ def setcar(self, car_val: Data) -> None:
90
+ self._car = car_val
91
+ def setcdr(self, cdr_val: Data) -> None:
92
+ self._cdr = cdr_val
93
+ def car(self) -> Data:
94
+ return self._car
95
+ def cdr(self) -> Data:
96
+ return self._cdr
97
+
98
+ class Symbol(Data):
99
+ def __init__(self, s: str):
100
+ self._val = s
101
+ def issymbol(self) -> bool:
102
+ return True
103
+ def __str__(self) -> str:
104
+ return self._val
105
+ def value(self) -> str:
106
+ return self._val
107
+
108
+ class Integer(Data):
109
+ def __init__(self, i: int):
110
+ self._val = i
111
+ def isint(self) -> bool:
112
+ return True
113
+ def __str__(self) -> str:
114
+ return str(self._val)
115
+ def value(self) -> int:
116
+ return self._val
117
+
118
+ class String(Data):
119
+ def __init__(self, s: str):
120
+ self._val = s
121
+ def isstr(self) -> bool:
122
+ return True
123
+ def __str__(self) -> str:
124
+ return self._val # Des250429: f'"{self._val}"'로 했다가 바꾸었음
125
+ def value(self) -> str:
126
+ return self._val
127
+
128
+ class Builtin(Data):
129
+ def __init__(self, fn):
130
+ self._fun = fn
131
+ def isbuiltin(self) -> bool:
132
+ return not super().isbuiltin()
133
+ def __str__(self) -> str:
134
+ fname = f"{self._fun}".split()[2]
135
+ return f"#<내장 함수: {fname}>"
136
+ def fun(self):
137
+ return self._fun
138
+
139
+ class Closure(Data):
140
+ def __init__(self, env: Data, params: Data, body: Data):
141
+ ## commented out for ch 10 (variadic)
142
+ # if not islist(params) or not islist(body):
143
+ # raise ErrSyntax() ####
144
+ # allsymbols(params)
145
+ if not islist(body):
146
+ raise ErrSyntax()
147
+ p = params
148
+ while not p.isnil():
149
+ if p.issymbol(): # the last symbol such as c in (f a b . c)
150
+ break
151
+ elif not p.ispair() or not car(p).issymbol():
152
+ raise ErrType("<#클로저>")
153
+ p = cdr(p) # pyright: ignore[reportArgumentType]
154
+ self._val = cons(env, cons(params, body))
155
+ def isclosure(self) -> bool:
156
+ return not super().isclosure()
157
+ def __str__(self) -> str:
158
+ return f"#<클로저>"
159
+ def val(self) -> Data: # returns the closure value (lambda)
160
+ return self._val
161
+ def env(self) -> Data:
162
+ return car(self._val) # pyright: ignore[reportArgumentType]
163
+ def params(self) -> Data:
164
+ return car(cdr(self._val)) # pyright: ignore[reportArgumentType]
165
+ def body(self) -> Data:
166
+ return cdr(cdr(self._val)) # pyright: ignore[reportArgumentType]
167
+
168
+ class Macro(Data):
169
+ def __init__(self, env: Data, params: Data, body: Data):
170
+ if not islist(body):
171
+ raise ErrSyntax()
172
+ p = params
173
+ while not p.isnil():
174
+ if p.issymbol(): # the last symbol such as c in (f a b . c)
175
+ break
176
+ elif not p.ispair() or not car(p).issymbol():
177
+ raise ErrType("<#매크로>")
178
+ p = cdr(p) # pyright: ignore[reportArgumentType]
179
+ self._val = cons(env, cons(params, body))
180
+ def ismacro(self) -> bool:
181
+ return True
182
+ def __str__(self) -> str:
183
+ return f"#<매크로>"
184
+ def val(self) -> Data: # returns the closure value (lambda)
185
+ return self._val
186
+
187
+ def cons(car_val: Data, cdr_val: Data) -> Data:
188
+ return Pair(car_val, cdr_val)
189
+
190
+ def car(p: Data) -> Data:
191
+ return p.car()
192
+
193
+ def cdr(p: Data) -> Data:
194
+ return p.cdr()
195
+
196
+ def mkint(ival: int) -> Data:
197
+ return Integer(ival)
198
+
199
+ def mksym(sval: str) -> Data:
200
+ return Symbol(sval)
201
+
202
+ def mkstr(sval: str) -> Data:
203
+ return String(sval)
204
+
205
+ def mkbuiltin(fn) -> Data:
206
+ return Builtin(fn)
207
+
208
+ def mkclosure(env: Data, params: Data, body: Data) -> Data:
209
+ return Closure(env, params, body)
210
+
211
+ def mkmacro(env: Data, params: Data, body: Data) -> Data:
212
+ return Macro(env, params, body)
213
+
214
+
215
+ nil = Nil()
216
+
217
+ def islist(d: Data) -> bool:
218
+ if d.isnil():
219
+ return True
220
+ else:
221
+ return d.ispair() and islist(cdr(d)) # pyright: ignore[reportArgumentType]
222
+ # Bug_20230104_a: cdr(d).ispair() -> islist(cdr(d))
223
+
224
+ def cplist(ls: Data) -> Data:
225
+ if ls.isnil():
226
+ return nil
227
+ head = cons(car(ls), nil) # pyright: ignore[reportArgumentType]
228
+ prev = head
229
+ ls = cdr(ls) # pyright: ignore[reportArgumentType]
230
+ while not ls.isnil():
231
+ prev.setcdr(cons(car(ls), nil)) # pyright: ignore[reportAttributeAccessIssue, reportArgumentType]
232
+ prev = cdr(prev) # pyright: ignore[reportArgumentType]
233
+ ls = cdr(ls) # pyright: ignore[reportArgumentType]
234
+ return head
235
+
236
+ def allsymbols(params: Data) -> None:
237
+ p = params
238
+ while not p.isnil():
239
+ if not car(p).issymbol(): # pyright: ignore[reportArgumentType]
240
+ raise ErrType("<#클로저>")
241
+ p = cdr(p) # pyright: ignore[reportArgumentType]
242
+
243
+ if __name__ == '__main__':
244
+ print(mkint(1910))
245
+ print(mksym("안녕"))
246
+ print(mkstr("안녕, 문자열?"))
247
+ print(cons(mkint(8), cons(mkint(2), cons(mkint(9), nil))))
248
+ print(cons(mkint(3), mkint(4)))
@@ -0,0 +1,40 @@
1
+ #coding: utf-8
2
+
3
+ import sys
4
+
5
+ IsVerbose = False
6
+
7
+ def eprint(*args, **kwargs) -> None:
8
+ '''stderr에 출력하는 함수'''
9
+ print(*args, file=sys.stderr, **kwargs)
10
+
11
+ # making the hierarchy of Errors
12
+ # To do: enriching the arguments of errors
13
+ # translate into Korean
14
+
15
+ class ErrLisp(Exception):
16
+ pass
17
+
18
+ class ErrSyntax(ErrLisp):
19
+ def __init__(self:ErrLisp):
20
+ pass
21
+ def __str__(self:ErrLisp) -> str:
22
+ return "구문 오류"
23
+
24
+ class ErrUnbound(ErrLisp):
25
+ def __init__(self, sym: str):
26
+ self.symname = sym
27
+ def __str__(self:ErrLisp) -> str:
28
+ return f"이름 '{self.symname}'을(를) 찾을 수 없습니다." # pyright: ignore[reportAttributeAccessIssue]
29
+
30
+ class ErrArgs(ErrLisp):
31
+ def __init__(self, fun: str):
32
+ self.funname = fun
33
+ def __str__(self:ErrLisp) -> str:
34
+ return f"함수 {self.funname}: 인수 개수 오류입니다." # pyright: ignore[reportAttributeAccessIssue]
35
+
36
+ class ErrType(ErrLisp):
37
+ def __init__(self, fun: str):
38
+ self.funname = fun
39
+ def __str__(self:ErrLisp) -> str:
40
+ return f"함수 {self.funname}: 타입 오류입니다." # pyright: ignore[reportAttributeAccessIssue]