mirror of
https://github.com/erg-lang/erg.git
synced 2025-10-02 05:31:11 +00:00
Support Python 3.9 as tier-2
This commit is contained in:
parent
bf48ed0cb2
commit
54dbd1ec22
10 changed files with 26 additions and 187 deletions
|
@ -159,7 +159,7 @@
|
|||
|
||||
## Requirements
|
||||
|
||||
A [Python3 (3.7 | 3.8 | 3.10 | 3.11)](https://www.python.org/) interpreter is required. If it is already installed on your machine, no setup is required.
|
||||
A [Python3 (3.7~3.11)](https://www.python.org/) interpreter is required. If it is already installed on your machine, no setup is required.
|
||||
|
||||
## Installation
|
||||
|
||||
|
|
|
@ -159,7 +159,7 @@
|
|||
|
||||
## Requirements
|
||||
|
||||
[Python3](https://www.python.org/)インタープリタがインストールされている必要があります。すでにインストールされているならセットアップは不要です。
|
||||
[Python3 (3.7~3.11)](https://www.python.org/)インタープリタがインストールされている必要があります。すでにインストールされているならセットアップは不要です。
|
||||
|
||||
## インストール
|
||||
|
||||
|
|
|
@ -159,7 +159,7 @@
|
|||
|
||||
## 要求
|
||||
|
||||
[Python3](https://www.python.org/) 解释器是必需的。如果计算机上已安装它,则无需进行任何设置
|
||||
[Python3 (3.7~3.11)](https://www.python.org/) 解释器是必需的。如果计算机上已安装它,则无需进行任何设置
|
||||
|
||||
## 安装
|
||||
|
||||
|
|
|
@ -159,7 +159,7 @@
|
|||
|
||||
## 要求
|
||||
|
||||
[Python3 (3.10.x)](https://www.python.org/) 解釋器是必需的。如果計算機上已安裝它,則無需進行任何設置
|
||||
[Python3 (3.7~3.11)](https://www.python.org/) 解釋器是必需的。如果計算機上已安裝它,則無需進行任何設置
|
||||
|
||||
## 安裝
|
||||
|
||||
|
|
|
@ -1702,11 +1702,11 @@ impl PyCodeGenerator {
|
|||
self.write_instr(Opcode310::JUMP_ABSOLUTE);
|
||||
self.write_arg(idx_for_iter / 2);
|
||||
}
|
||||
Some(8) => {
|
||||
Some(9 | 8 | 7) => {
|
||||
self.write_instr(Opcode308::JUMP_ABSOLUTE);
|
||||
self.write_arg(idx_for_iter);
|
||||
}
|
||||
_ => todo!(),
|
||||
_ => todo!("not supported Python version"),
|
||||
}
|
||||
let idx_end = self.lasti();
|
||||
self.calc_edit_jump(idx_for_iter + 1, idx_end - idx_for_iter - 2);
|
||||
|
@ -2172,8 +2172,8 @@ impl PyCodeGenerator {
|
|||
"with!" => match self.py_version.minor {
|
||||
Some(11) => self.emit_with_instr_311(args),
|
||||
Some(10) => self.emit_with_instr_310(args),
|
||||
Some(8) => self.emit_with_instr_308(args),
|
||||
_ => todo!(),
|
||||
Some(9 | 8 | 7) => self.emit_with_instr_308(args),
|
||||
_ => todo!("not supported Python version"),
|
||||
},
|
||||
// "pyimport" | "py" are here
|
||||
_ => {
|
||||
|
@ -3005,11 +3005,7 @@ impl PyCodeGenerator {
|
|||
}
|
||||
|
||||
fn load_in_op(&mut self) {
|
||||
let mod_name = if self.py_version.minor >= Some(10) {
|
||||
Identifier::public("_erg_std_prelude")
|
||||
} else {
|
||||
Identifier::public("_erg_std_prelude_old")
|
||||
};
|
||||
let mod_name = Identifier::public("_erg_std_prelude");
|
||||
self.emit_global_import_items(
|
||||
mod_name,
|
||||
vec![(
|
||||
|
@ -3021,11 +3017,7 @@ impl PyCodeGenerator {
|
|||
}
|
||||
|
||||
fn load_mutate_op(&mut self) {
|
||||
let mod_name = if self.py_version.minor >= Some(10) {
|
||||
Identifier::public("_erg_std_prelude")
|
||||
} else {
|
||||
Identifier::public("_erg_std_prelude_old")
|
||||
};
|
||||
let mod_name = Identifier::public("_erg_std_prelude");
|
||||
self.emit_global_import_items(
|
||||
mod_name,
|
||||
vec![(
|
||||
|
@ -3062,11 +3054,7 @@ impl PyCodeGenerator {
|
|||
self.emit_call_instr(1, Method);
|
||||
self.stack_dec();
|
||||
self.emit_pop_top();
|
||||
let erg_std_mod = if self.py_version.minor >= Some(10) {
|
||||
Identifier::public("_erg_std_prelude")
|
||||
} else {
|
||||
Identifier::public("_erg_std_prelude_old")
|
||||
};
|
||||
let erg_std_mod = Identifier::public("_erg_std_prelude");
|
||||
// escaping
|
||||
self.emit_global_import_items(
|
||||
erg_std_mod.clone(),
|
||||
|
|
|
@ -24,7 +24,7 @@ class Nat(Int):
|
|||
class NatMut(IntMut): # and Nat
|
||||
value: Nat
|
||||
|
||||
def __init__(self, n):
|
||||
def __init__(self, n: Nat):
|
||||
self.value = n
|
||||
def __repr__(self):
|
||||
return self.value.__repr__()
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
from _erg_nat import Nat
|
||||
from _erg_str import Str
|
||||
|
||||
from collections.abc import Iterable, Sequence, Iterator, Container
|
||||
# from collections.abc import Iterable, Sequence, Iterator, Container
|
||||
|
||||
class Range:
|
||||
def __init__(self, start, end):
|
||||
|
@ -15,6 +15,7 @@ class Range:
|
|||
return res
|
||||
else:
|
||||
raise IndexError("Index out of range")
|
||||
# TODO: for Str, etc.
|
||||
def __len__(self):
|
||||
if self.start in self:
|
||||
if self.end in self:
|
||||
|
@ -33,9 +34,9 @@ class Range:
|
|||
def __iter__(self):
|
||||
return RangeIterator(rng=self)
|
||||
|
||||
Sequence.register(Range)
|
||||
Container.register(Range)
|
||||
Iterable.register(Range)
|
||||
# Sequence.register(Range)
|
||||
# Container.register(Range)
|
||||
# Iterable.register(Range)
|
||||
|
||||
# represents `start<..end`
|
||||
class LeftOpenRange(Range):
|
||||
|
@ -92,4 +93,4 @@ class RangeIterator:
|
|||
return result
|
||||
raise StopIteration
|
||||
|
||||
Iterator.register(RangeIterator)
|
||||
# Iterator.register(RangeIterator)
|
||||
|
|
|
@ -1,18 +1,18 @@
|
|||
from typing import TypeVar, Union, _SpecialForm, _type_check
|
||||
# from typing import TypeVar, Union, _SpecialForm, _type_check
|
||||
|
||||
class Error:
|
||||
def __init__(self, message):
|
||||
self.message = message
|
||||
|
||||
T = TypeVar("T")
|
||||
@_SpecialForm
|
||||
# T = TypeVar("T")
|
||||
# @_SpecialForm
|
||||
def Result(self, parameters):
|
||||
"""Result type.
|
||||
|
||||
Result[T] is equivalent to Union[T, Error].
|
||||
"""
|
||||
arg = _type_check(parameters, f"{self} requires a single type.")
|
||||
return Union[arg, Error]
|
||||
# arg = _type_check(parameters, f"{self} requires a single type.")
|
||||
return [arg, Error]
|
||||
|
||||
def is_ok(obj: Result[T]) -> bool:
|
||||
def is_ok(obj) -> bool:
|
||||
return not isinstance(obj, Error)
|
||||
|
|
|
@ -1,152 +0,0 @@
|
|||
class Error:
|
||||
def __init__(self, message):
|
||||
self.message = message
|
||||
|
||||
def is_ok(obj) -> bool:
|
||||
return not isinstance(obj, Error)
|
||||
|
||||
def in_operator(x, y):
|
||||
if type(y) == type:
|
||||
if isinstance(x, y):
|
||||
return True
|
||||
elif is_ok(y.try_new(x)):
|
||||
return True
|
||||
# TODO: trait check
|
||||
return False
|
||||
elif (type(y) == list or type(y) == set) and type(y[0]) == type:
|
||||
# FIXME:
|
||||
type_check = in_operator(x[0], y[0])
|
||||
len_check = len(x) == len(y)
|
||||
return type_check and len_check
|
||||
elif type(y) == dict and type(next(iter(y.keys()))) == type:
|
||||
# TODO:
|
||||
type_check = True # in_operator(x[next(iter(x.keys()))], next(iter(y.keys())))
|
||||
len_check = len(x) >= len(y)
|
||||
return type_check and len_check
|
||||
else:
|
||||
return x in y
|
||||
|
||||
class Nat(int):
|
||||
def try_new(i: int): # -> Result[Nat]
|
||||
if i >= 0:
|
||||
return Nat(i)
|
||||
else:
|
||||
return Error("Nat can't be negative")
|
||||
|
||||
def times(self, f):
|
||||
for _ in range(self):
|
||||
f()
|
||||
|
||||
class Bool(Nat):
|
||||
def try_new(b: bool): # -> Result[Nat]
|
||||
if b == True or b == False:
|
||||
return Bool(b)
|
||||
else:
|
||||
return Error("Bool can't be other than True or False")
|
||||
|
||||
def __str__(self) -> str:
|
||||
if self:
|
||||
return "True"
|
||||
else:
|
||||
return "False"
|
||||
def __repr__(self) -> str:
|
||||
return self.__str__()
|
||||
|
||||
class Str(str):
|
||||
def __instancecheck__(cls, obj):
|
||||
return obj == Str or obj == str
|
||||
|
||||
def try_new(s: str): # -> Result[Nat]
|
||||
if isinstance(s, str):
|
||||
return Str(s)
|
||||
else:
|
||||
return Error("Str can't be other than str")
|
||||
|
||||
class Range:
|
||||
def __init__(self, start, end):
|
||||
self.start = start
|
||||
self.end = end
|
||||
def __contains__(self, item):
|
||||
pass
|
||||
def __getitem__(self, item):
|
||||
pass
|
||||
def __len__(self):
|
||||
pass
|
||||
def __iter__(self):
|
||||
return RangeIterator(rng=self)
|
||||
|
||||
# represents `start<..end`
|
||||
class LeftOpenRange(Range):
|
||||
def __contains__(self, item):
|
||||
return self.start < item <= self.end
|
||||
def __getitem__(self, item):
|
||||
return NotImplemented
|
||||
def __len__(self):
|
||||
return NotImplemented
|
||||
|
||||
# represents `start..<end`
|
||||
class RightOpenRange(Range):
|
||||
def __contains__(self, item):
|
||||
return self.start <= item < self.end
|
||||
def __getitem__(self, item):
|
||||
return NotImplemented
|
||||
def __len__(self):
|
||||
return NotImplemented
|
||||
|
||||
# represents `start<..<end`
|
||||
class OpenRange(Range):
|
||||
def __contains__(self, item):
|
||||
return self.start < item < self.end
|
||||
def __getitem__(self, item):
|
||||
return NotImplemented
|
||||
def __len__(self):
|
||||
return NotImplemented
|
||||
|
||||
# represents `start..end`
|
||||
class ClosedRange(Range):
|
||||
def __contains__(self, item):
|
||||
return self.start <= item <= self.end
|
||||
def __getitem__(self, item):
|
||||
return NotImplemented
|
||||
def __len__(self):
|
||||
return NotImplemented
|
||||
|
||||
class RangeIterator:
|
||||
def __init__(self, rng):
|
||||
self.rng = rng
|
||||
self.needle = self.rng.start
|
||||
if type(self.rng.start) == int:
|
||||
if not(self.needle in self.rng):
|
||||
self.needle += 1
|
||||
elif type(self.rng.start) == str:
|
||||
if not(self.needle in self.rng):
|
||||
self.needle = chr(ord(self.needle) + 1)
|
||||
else:
|
||||
if not(self.needle in self.rng):
|
||||
self.needle = self.needle.incremented()
|
||||
|
||||
def __iter__(self):
|
||||
return self
|
||||
|
||||
def __next__(self):
|
||||
if type(self.rng.start) == int:
|
||||
if self.needle in self.rng:
|
||||
result = self.needle
|
||||
self.needle += 1
|
||||
return result
|
||||
elif type(self.rng.start) == str:
|
||||
if self.needle in self.rng:
|
||||
result = self.needle
|
||||
self.needle = chr(ord(self.needle) + 1)
|
||||
return result
|
||||
else:
|
||||
if self.needle in self.rng:
|
||||
result = self.needle
|
||||
self.needle = self.needle.incremented()
|
||||
return result
|
||||
raise StopIteration
|
||||
|
||||
class Array(list):
|
||||
def push(self, value):
|
||||
self.append(value)
|
||||
return self
|
|
@ -72,6 +72,8 @@ fn _exec_vm(file_path: &'static str) -> Result<i32, CompileErrors> {
|
|||
};
|
||||
// cfg.target_version = Some(PythonVersion::new(3, Some(8), Some(10))); // your Python's version
|
||||
// cfg.py_magic_num = Some(3413); // in (most) 3.8.x
|
||||
// cfg.target_version = Some(PythonVersion::new(3, Some(9), Some(0)));
|
||||
// cfg.py_magic_num = Some(3425); // in (most) 3.9.x
|
||||
// cfg.target_version = Some(PythonVersion::new(3, Some(10), Some(6)));
|
||||
// cfg.py_magic_num = Some(3439); // in (most) 3.10.x
|
||||
cfg.target_version = Some(PythonVersion::new(3, Some(11), Some(0)));
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue