Skip to content

Commit

Permalink
Add cherry-picked release candidates for 1.1.7 (kyuridenamida#199)
Browse files Browse the repository at this point in the history
* 整数判定において、先頭が0だったり、文字数が20以上だったらFalseにするように (kyuridenamida#172)

* 整数判定において、先頭が0だったり、文字数が20以上だったらFalseにするように

* answer.txtを変更

* test_mod_caseをstringに

* Makes gen command retry with exponential backoff (kyuridenamida#174)

Previously, gen command retries with fixed delay of 1.5 seconds indefinitely. It could hurt the service especially when they are experiencing overloaded traffic. This patch changes the retry strategy with exponential backoff starting from 1.5 seconds to 60 seconds at maximum. The gen commands aborts by EnvironmentInitializationError exception after 10 attempts.

* kyuridenamida#186 Support \dots in input formats (kyuridenamida#187)

* C++言語アップデートへの対応 (kyuridenamida#191)

* Fix cpp language configs

* Update atcodertools/common/language.py

Co-authored-by: DNEK <[email protected]>

Co-authored-by: Kazuma Mikami <[email protected]>
Co-authored-by: DNEK <[email protected]>

* Pythonの言語アップデートに対応 (kyuridenamida#192)

* Fix crash in new judgement using Python

* Fix bugs of Python2 submissions in old judgement

Co-authored-by: Matts966 <[email protected]>

* 新しい言語のバージョンに対応 (kyuridenamida#196)

* 新しい言語のバージョンに対応

* gen, submitを新しいのに対応

* Fix regexps

Co-authored-by: Kazuma Mikami <[email protected]>

* Fix style

* Update mock pages

* Fix submissions

* Fix flake8

Co-authored-by: chaemon <[email protected]>
Co-authored-by: Yuki Hamada <[email protected]>
Co-authored-by: Takaaki Hirano <[email protected]>
Co-authored-by: DNEK <[email protected]>
Co-authored-by: Matts966 <[email protected]>
Co-authored-by: Matts966 <[email protected]>
  • Loading branch information
7 people committed May 17, 2020
1 parent 1cae3ec commit daddb88
Showing 1 changed file with 229 additions and 0 deletions.
229 changes: 229 additions & 0 deletions atcodertools/codegen/code_generators/python_backup.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,229 @@
from typing import Dict, Any, Optional, List
import re

from atcodertools.codegen.code_style_config import CodeStyleConfig
from atcodertools.codegen.models.code_gen_args import CodeGenArgs
from atcodertools.codegen.template_engine import render
from atcodertools.fmtprediction.models.format import (
Pattern,
SingularPattern,
ParallelPattern,
TwoDimensionalPattern,
Format)
from atcodertools.fmtprediction.models.type import Type
from atcodertools.fmtprediction.models.variable import Variable


def _loop_header(var: Variable, for_second_index: bool):
if for_second_index:
index = var.second_index
loop_var = "j"
else:
index = var.first_index
loop_var = "i"

return "for {loop_var} in range({length}):".format(
loop_var=loop_var,
length=_insert_space_around_operators(index.get_length()))


def _insert_space_around_operators(code):
code = str(code)
precode = code
pattern = r"([0-9a-zA-Z_])([+\-\*/])([0-9a-zA-Z_])"
code = re.sub(pattern, r"\1 \2 \3", code)
while precode != code:
precode = code
code = re.sub(pattern, r"\1 \2 \3", code)
return code


class Python3CodeGenerator:

def __init__(self,
format_: Optional[Format[Variable]],
config: CodeStyleConfig):
self._format = format_
self._config = config

def generate_parameters(self) -> Dict[str, Any]:
if self._format is None:
return dict(prediction_success=False)

return dict(formal_arguments=self._formal_arguments(),
actual_arguments=self._actual_arguments(),
input_part=self._input_part(),
prediction_success=True)

def _input_part(self):
lines = []
for pattern in self._format.sequence:
lines += self._render_pattern(pattern)
return "\n{indent}".format(indent=self._indent(1)).join(lines)

def _convert_type(self, type_: Type) -> str:
if type_ == Type.float:
return "float"
elif type_ == Type.int:
return "int"
elif type_ == Type.str:
return "str"
else:
raise NotImplementedError

def _get_declaration_type(self, var: Variable):
ctype = self._convert_type(var.type)
for _ in range(var.dim_num()):
ctype = "List[{}]".format(ctype)
if var.dim_num():
ctype = '"{}"'.format(ctype)
return ctype

def _actual_arguments(self) -> str:
"""
:return the string form of actual arguments e.g. "N, K, a"
"""
return ", ".join([v.name for v in self._format.all_vars()])

def _formal_arguments(self):
"""
:return the string form of formal arguments e.g. "N: int, K: int, a: List[int]"
"""
return ", ".join([
"{name}: {decl_type}".format(
decl_type=self._get_declaration_type(v),
name=v.name)
for v in self._format.all_vars()
])

def _generate_declaration(self, var: Variable):
"""
:return: Create declaration part E.g. array[1..n] -> array = [int()] * (n-1+1) # type: List[int]
"""
if var.dim_num() == 0:
dims = []
elif var.dim_num() == 1:
dims = [var.first_index.get_length()]
elif var.dim_num() == 2:
dims = [var.first_index.get_length(),
var.second_index.get_length()]
else:
raise NotImplementedError

ctype = self._convert_type(var.type)
if len(dims) == 0:
ctor = "{}()".format(ctype)
elif len(dims) == 1:
ctor = "[{ctype}()] * ({dim})".format(
ctype=ctype, dim=_insert_space_around_operators(dims[0]))
else:
ctor = "[{ctype}()] * ({dim})".format(
ctype=ctype, dim=_insert_space_around_operators(dims[0]))
for dim in dims[-2::-1]:
ctor = "[{ctor} for _ in range({dim})]".format(
ctor=ctor, dim=_insert_space_around_operators(dim))

line = "{name} = {constructor} # type: {decl_type}".format(
name=var.name,
decl_type=self._get_declaration_type(var),
constructor=ctor
)
return line

def _input_code_for_token(self, type_: Type) -> str:
if type_ == Type.float:
return "float(next(tokens))"
elif type_ == Type.int:
return "int(next(tokens))"
elif type_ == Type.str:
return "next(tokens)"
else:
raise NotImplementedError

def _input_code_for_single_pattern(self, pattern: Pattern) -> str:
assert len(pattern.all_vars()) == 1
var = pattern.all_vars()[0]

if isinstance(pattern, SingularPattern):
input_ = self._input_code_for_token(var.type)

elif isinstance(pattern, ParallelPattern):
input_ = "[{input_} for _ in range({length})]".format(
input_=self._input_code_for_token(var.type),
length=_insert_space_around_operators(var.first_index.get_length()))

elif isinstance(pattern, TwoDimensionalPattern):
input_ = "[[{input_} for _ in range({second_length})] for _ in range({first_length})]".format(
input_=self._input_code_for_token(var.type),
first_length=_insert_space_around_operators(
var.first_index.get_length()),
second_length=_insert_space_around_operators(
var.second_index.get_length()))

else:
raise NotImplementedError

return "{name} = {input_} # type: {type_}".format(
name=var.name,
input_=input_,
type_=self._get_declaration_type(var))

@staticmethod
def _get_var_name(var: Variable):
name = var.name
if var.dim_num() >= 1:
name += "[i]"
if var.dim_num() >= 2:
name += "[j]"
return name

def _input_code_for_non_single_pattern(self, pattern: Pattern) -> List[str]:
lines = []
for var in pattern.all_vars():
lines.append(self._generate_declaration(var))
representative_var = pattern.all_vars()[0]

if isinstance(pattern, SingularPattern):
assert False

elif isinstance(pattern, ParallelPattern):
lines.append(_loop_header(representative_var, False))
for var in pattern.all_vars():
lines.append("{indent}{name} = {input_}".format(indent=self._indent(1),
name=self._get_var_name(
var),
input_=self._input_code_for_token(var.type)))

elif isinstance(pattern, TwoDimensionalPattern):
lines.append(_loop_header(representative_var, False))
lines.append(
"{indent}{line}".format(indent=self._indent(1), line=_loop_header(representative_var, True)))
for var in pattern.all_vars():
lines.append("{indent}{name} = {input_}".format(indent=self._indent(2),
name=self._get_var_name(
var),
input_=self._input_code_for_token(var.type)))

else:
raise NotImplementedError
return lines

def _render_pattern(self, pattern: Pattern):
if len(pattern.all_vars()) == 1:
return [self._input_code_for_single_pattern(pattern)]
else:
return self._input_code_for_non_single_pattern(pattern)

def _indent(self, depth):
return self._config.indent(depth)


def main(args: CodeGenArgs) -> str:
code_parameters = Python3CodeGenerator(
args.format, args.config).generate_parameters()
return render(
args.template,
mod=args.constants.mod,
yes_str=args.constants.yes_str,
no_str=args.constants.no_str,
**code_parameters)

0 comments on commit daddb88

Please sign in to comment.