Loading .flake8 0 → 100644 +30 −0 Original line number Original line Diff line number Diff line [flake8] ignore = # usual defaults: # continuation line under-indented for hanging indent E121 # closing bracket does not match indentation of opening bracket’s line E123 # continuation line over-indented for hanging indent E126 # closing bracket is missing indentation E133 # E226 missing whitespace around arithmetic operator # E241 multiple spaces after ‘,’ # E242 tab after ‘,’ # multiple statements on one line (def) E704 # line break before binary operator W503 # W504 line break after binary operator # W505 doc line too long (82 > 79 characters) # other suppressions # type annotation on self ANN101 per-file-ignores = evalweb/examples.py:FS003 # vim: expandtab ft=dosini evalweb/evalweb.py +44 −22 Original line number Original line Diff line number Diff line Loading @@ -34,13 +34,18 @@ types = {'DFA': 'DFA', # forms from variants above # forms from variants above class TypeForm(FlaskForm): class TypeForm(FlaskForm): make = RadioField('Typ', choices=list(types.items()), default='DFA', coerce=str) make = RadioField('Typ', choices=list(types.items()), default='DFA', coerce=str) class TaskForm(FlaskForm): class TaskForm(FlaskForm): make = RadioField('Task', choices=list(tasks.items()), default='DFA', coerce=str) make = RadioField('Task', choices=list(tasks.items()), default='DFA', coerce=str) class ConvertForm(FlaskForm): class ConvertForm(FlaskForm): make = RadioField('Convert', choices=list(convs.items()), default='DFA', coerce=str) make = RadioField('Convert', choices=list(convs.items()), default='DFA', coerce=str) @bp.route('/compare', methods=('GET', 'POST')) @bp.route('/compare', methods=('GET', 'POST')) Loading @@ -50,7 +55,7 @@ def compare(): student_area = "" # areas remembers user input or replace it with examples student_area = "" # areas remembers user input or replace it with examples teacher_area = "" teacher_area = "" if request.method == 'POST' and 'submit_button' in request.form: # submit action if request.method == 'POST' and 'submit_button' in request.form: teacher_type = teacher_form.make.data teacher_type = teacher_form.make.data teacher_string = request.form['teacher_string'] teacher_string = request.form['teacher_string'] student_type = student_form.make.data student_type = student_form.make.data Loading @@ -59,35 +64,46 @@ def compare(): teacher_area = teacher_string teacher_area = teacher_string if student_string == "" or teacher_string == "": if student_string == "" or teacher_string == "": return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") checker = WebChecker(student_string=student_string, task=student_type) checker = WebChecker(student_string=student_string, task=student_type) result = checker.compare(teacher_string=teacher_string, teacher_type=teacher_type) result = checker.compare(teacher_string=teacher_string, teacher_type=teacher_type) if not isinstance(result, bool): if not isinstance(result, bool): return render_template('parsing_error.html') return render_template('parsing_error.html') extra_word_ce, missing_word_ce, inf = None, None, None extra_word_ce, missing_word_ce, inf = None, None, None if not result and checker.eq is not None: # languages aren't equivalent if not result and checker.eq is not None: # languages not equivalent extra_word_ce = checker.eq.left_counterexample extra_word_ce = checker.eq.left_counterexample missing_word_ce = checker.eq.right_counterexample missing_word_ce = checker.eq.right_counterexample inf = checker.eq.inf inf = checker.eq.inf return render_template('result_compare.html', compare=True, ok=result, return render_template('result_compare.html', compare=True, ok=result, inf=inf, inf=inf, task_solved=checker.task_solved, task_solved=checker.task_solved, alphabets=checker.alphabets, alphabets=checker.alphabets, extra_word_ce=extra_word_ce, missing_word_ce=missing_word_ce, extra_word_ce=extra_word_ce, is_task=checker.is_task, img_src=checker.img_src, langs=checker.languages, missing_word_ce=missing_word_ce, teacher=checker.teacher, student=checker.student, is_task=checker.is_task, teacher_type_string=types[checker.teacher.task], student_type_string=tasks[checker.student.task]) img_src=checker.img_src, langs=checker.languages, teacher=checker.teacher, student=checker.student, teacher_type_string=types[checker.teacher.task], student_type_string=tasks[checker.student.task]) if request.method == 'POST' and 'example_button' in request.form: if request.method == 'POST' and 'example_button' in request.form: teacher_type = teacher_form.make.data # of which types examples should be # of which types examples should be teacher_type = teacher_form.make.data student_type = student_form.make.data student_type = student_form.make.data if (teacher_type, student_type) in examples: if (teacher_type, student_type) in examples: teacher_area, student_area = examples[(teacher_type, student_type)] teacher_area, student_area = examples[(teacher_type, student_type)] return render_template('compare.html', student_form=student_form, teacher_form=teacher_form, return render_template('compare.html', student_area=student_area, teacher_area=teacher_area) student_form=student_form, teacher_form=teacher_form, student_area=student_area, teacher_area=teacher_area) # analogical to compare, only with just one input formalism # analogical to compare, only with just one input formalism Loading @@ -104,26 +120,32 @@ def convert(): student_area = student_string student_area = student_string if student_string == "": if student_string == "": return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") checker = WebChecker(student_string=student_string, task=task) checker = WebChecker(student_string=student_string, task=task) try: try: output = checker.convert(student_type=student_type) output = checker.convert(student_type=student_type) except ParsingError as ex: except ParsingError: return render_template('parsing_error.html') return render_template('parsing_error.html') student = Language(string=student_string, task=student_type) student = Language(string=student_string, task=student_type) is_task = student.gen_is_task(task=task) is_task = student.gen_is_task(task=task) return render_template('result_convert.html', compare=False, student_string=student_string, return render_template('result_convert.html', compare=False, student_type=types[student_type], task=tasks[task], output=output, is_task=is_task) student_string=student_string, student_type=types[student_type], task=tasks[task], output=output, is_task=is_task) if request.method == 'POST' and 'example_button' in request.form: if request.method == 'POST' and 'example_button' in request.form: student_type = student_form.make.data student_type = student_form.make.data if student_type in convert_examples: if student_type in convert_examples: student_area = convert_examples[student_type] student_area = convert_examples[student_type] return render_template('convert.html', student_form=student_form, task_form=task_form, student_area=student_area) return render_template('convert.html', student_form=student_form, task_form=task_form, student_area=student_area) @bp.route('/userref') @bp.route('/userref') Loading evalweb/examples.py +6 −5 Original line number Original line Diff line number Diff line Loading @@ -8,11 +8,12 @@ convert_examples: Dict[str, str] = {} teacher_dfa = "(0,a)=1 (1,b)=0 final={0}" teacher_dfa = "(0,a)=1 (1,b)=0 final={0}" student_dfa = "(A,a)=B (B,b)=C (C,a)=B final={A,C}" student_dfa = "(A,a)=B (B,b)=C (C,a)=B final={A,C}" teacher_dfa_total = parser.dfa_to_str(parser.str_to_dfa(teacher_dfa).total()) teacher_dfa_total = parser.dfa_to_str(parser.str_to_dfa(teacher_dfa).total()) teacher_efa = "(A,a)={B} (A,\e)={D} (B,b)={A} final={A,D}" teacher_efa = r"(A,a)={B} (A,\e)={D} (B,b)={A} final={A,D}" student_nfa = parser.nfa_to_str(parser.str_to_nfa(teacher_efa).eliminate_epsilon()) student_nfa = parser.nfa_to_str(parser.str_to_nfa(teacher_efa) student_gra = "S -> aS' | \e\nS' -> bA | b\nA -> aS'" .eliminate_epsilon()) student_gra = r"S -> aS' | \e\nS' -> bA | b\nA -> aS'" student_reg = "(ab)^*" student_reg = "(ab)^*" student_efa = "(A,a)={B} (A,\e)={D} (B,b)={C} (C,a)={B} final={C,D}" student_efa = r"(A,a)={B} (A,\e)={D} (B,b)={C} (C,a)={B} final={C,D}" examples[('DFA', 'DFA')] = (teacher_dfa, student_dfa) examples[('DFA', 'DFA')] = (teacher_dfa, student_dfa) examples[('DFA', 'TOT')] = (teacher_dfa, teacher_dfa_total) examples[('DFA', 'TOT')] = (teacher_dfa, teacher_dfa_total) Loading evalweb/web_checker.py +42 −30 Original line number Original line Diff line number Diff line import lib.reg as reg import lib.reg as reg from lib.parsing.parser import Parser, ParsingError from lib.parsing.parser import Parser, ParsingError from lib.checker import transform, dfa_transform, nfa_transform, check_task, check_alphabets from lib.checker import transform, dfa_transform, nfa_transform, check_task, \ check_alphabets from typing import List, Tuple from typing import List, Tuple from enum import Enum from enum import Enum import enum import enum Loading @@ -14,7 +15,7 @@ class Size(Enum): class Language: # contains information about formalism and its language class Language: # contains information about formalism and its language def __init__(self, string: str, task: str = "DFA"): def __init__(self, string: str, task: str = "DFA") -> None: self.string = string self.string = string self.task = task self.task = task self.dfa = None self.dfa = None Loading @@ -24,7 +25,7 @@ class Language: # contains information about formalism and its language self.example = None self.example = None self.gen_lang_html() self.gen_lang_html() def gen_lang_html(self): def gen_lang_html(self) -> None: parser = Parser() parser = Parser() dfa = dfa_transform(self.string, self.task) dfa = dfa_transform(self.string, self.task) self.minimal = parser.dfa_to_str(dfa.minimize().canonize()) self.minimal = parser.dfa_to_str(dfa.minimize().canonize()) Loading Loading @@ -74,7 +75,8 @@ class WebChecker: try: try: teacher = Language(string=teacher_string, task=teacher_type) teacher = Language(string=teacher_string, task=teacher_type) student = Language(string=student_string, task=self.task) student = Language(string=student_string, task=self.task) student_solution = transform(student_string, task) # only for task checking # only for task checking student_solution = transform(student_string, task) except ParsingError as ex: # Parsing error, don't continue except ParsingError as ex: # Parsing error, don't continue return ex.args return ex.args Loading @@ -83,15 +85,18 @@ class WebChecker: self.student = student self.student = student self.is_task = teacher.gen_is_task(task=self.task) self.is_task = teacher.gen_is_task(task=self.task) if isinstance(student_solution, reg.DFA) or isinstance(student_solution, reg.NFA): if isinstance(student_solution, reg.DFA) \ or isinstance(student_solution, reg.NFA): self.task_solved = check_task(student_solution, task) self.task_solved = check_task(student_solution, task) if teacher.size == Size.Empty and student.size == Size.Empty: if teacher.size == Size.Empty and student.size == Size.Empty: return self.task_solved == "" return self.task_solved == "" # if the alphabets aren't same, languages aren't equal (unless they are both empty) # if the alphabets aren't same, languages aren't equal (unless they are # both empty) alphabets = check_alphabets(student_alpha=student.dfa.characters, alphabets = check_alphabets(student_alpha=student.dfa.characters, teacher_alpha=teacher.dfa.characters, task=task) teacher_alpha=teacher.dfa.characters, task=task) if alphabets != "": if alphabets != "": self.alphabets = alphabets self.alphabets = alphabets Loading @@ -99,26 +104,26 @@ class WebChecker: self.eq = reg.DFA.is_equivalent(student.dfa, teacher.dfa) self.eq = reg.DFA.is_equivalent(student.dfa, teacher.dfa) self.img_src = self.relation(self.eq.left_counterexample is None and self.img_src = self.relation(self.eq.left_counterexample is None self.eq.right_counterexample is None) and self.eq.right_counterexample is None) if self.task_solved == "" and \ if self.task_solved == "" and \ self.eq.right_counterexample is None and \ self.eq.right_counterexample is None and \ self.eq.left_counterexample is None: self.eq.left_counterexample is None: return True return True return False return False def compare(self, teacher_string: str, teacher_type: str): def compare(self, teacher_string: str, teacher_type: str): # signal.alarm(50) # from fja_checker: here would kill the web # signal.alarm(50) # from fja_checker: here would kill the web try: try: return self.dfa_task(teacher_type=teacher_type, teacher_string=teacher_string, return self.dfa_task(teacher_type=teacher_type, task=self.task, student_string=self.student_string) teacher_string=teacher_string, task=self.task, student_string=self.student_string) except ParsingError as ex: except ParsingError as ex: return ex.args return ex.args # raise ParsingError(ex.args) # raise ParsingError(ex.args) def convert(self, student_type): def convert(self, student_type): try: try: parser = Parser() parser = Parser() Loading @@ -141,10 +146,11 @@ class WebChecker: return parser.nfa_to_str(nfa) return parser.nfa_to_str(nfa) if self.task == "GRA": if self.task == "GRA": return parser.reggrammar_to_str(nfa.nfa_to_reggrammar().eliminate_useless()) return parser.reggrammar_to_str(nfa.nfa_to_reggrammar() .eliminate_useless()) except ParsingError as ex: except ParsingError as ex: return ex.args return ex.args # FIXME # raise ParsingError(ex.args) # raise ParsingError(ex.args) except Exception as ex: except Exception as ex: Loading @@ -155,7 +161,8 @@ class WebChecker: teacher = self.teacher.dfa teacher = self.teacher.dfa # language 0 on picture: complement of both # language 0 on picture: complement of both self.languages[0] = self.language((reg.DFA.union(teacher, student)).complement()) self.languages[0] = self.language( (reg.DFA.union(teacher, student)).complement()) if not eq: if not eq: if self.eq.left_counterexample is not None: # extra word if self.eq.left_counterexample is not None: # extra word Loading @@ -166,17 +173,22 @@ class WebChecker: self.languages[2] = self.student self.languages[2] = self.student return "disjunction" return "disjunction" else: else: self.languages[1] = self.language(reg.DFA.subtraction(teacher, student)) self.languages[1] = self.language(reg.DFA.subtraction( self.languages[2] = self.language(reg.DFA.subtraction(student, teacher)) teacher, student)) self.languages[3] = self.language(reg.DFA.intersection(teacher, student)) self.languages[2] = self.language(reg.DFA.subtraction( student, teacher)) self.languages[3] = self.language(reg.DFA.intersection( teacher, student)) return "intersection" return "intersection" else: # teacher is subset of student else: # teacher is subset of student self.languages[1] = self.teacher self.languages[1] = self.teacher self.languages[2] = self.language(reg.DFA.subtraction(student, teacher)) self.languages[2] = self.language(reg.DFA.subtraction( student, teacher)) picture = "t_in_s" picture = "t_in_s" else: # student is subset of teacher else: # student is subset of teacher self.languages[1] = self.language(reg.DFA.subtraction(teacher, student)) self.languages[1] = self.language(reg.DFA.subtraction( teacher, student)) self.languages[2] = self.student self.languages[2] = self.student picture = "s_in_t" picture = "s_in_t" Loading @@ -186,9 +198,11 @@ class WebChecker: self.languages[0] = self.language(teacher.complement()) self.languages[0] = self.language(teacher.complement()) self.languages[1] = self.teacher self.languages[1] = self.teacher #if self.teacher.size == Size.Empty or self.student.size == Size.Universal: # if self.teacher.size == Size.Empty \ # or self.student.size == Size.Universal: # picture += "_empty" # picture += "_empty" if self.teacher.size == Size.Universal or self.student.size == Size.Universal: if self.teacher.size == Size.Universal \ or self.student.size == Size.Universal: picture += "_universal" picture += "_universal" if self.teacher.size == Size.Universal: if self.teacher.size == Size.Universal: self.languages.pop(0) self.languages.pop(0) Loading @@ -202,7 +216,5 @@ class WebChecker: parser = Parser() parser = Parser() return Language(parser.dfa_to_str(dfa)) return Language(parser.dfa_to_str(dfa)) def DFA_lines(self, str): def DFA_lines(self, str_: str) -> None: pass pass Loading
.flake8 0 → 100644 +30 −0 Original line number Original line Diff line number Diff line [flake8] ignore = # usual defaults: # continuation line under-indented for hanging indent E121 # closing bracket does not match indentation of opening bracket’s line E123 # continuation line over-indented for hanging indent E126 # closing bracket is missing indentation E133 # E226 missing whitespace around arithmetic operator # E241 multiple spaces after ‘,’ # E242 tab after ‘,’ # multiple statements on one line (def) E704 # line break before binary operator W503 # W504 line break after binary operator # W505 doc line too long (82 > 79 characters) # other suppressions # type annotation on self ANN101 per-file-ignores = evalweb/examples.py:FS003 # vim: expandtab ft=dosini
evalweb/evalweb.py +44 −22 Original line number Original line Diff line number Diff line Loading @@ -34,13 +34,18 @@ types = {'DFA': 'DFA', # forms from variants above # forms from variants above class TypeForm(FlaskForm): class TypeForm(FlaskForm): make = RadioField('Typ', choices=list(types.items()), default='DFA', coerce=str) make = RadioField('Typ', choices=list(types.items()), default='DFA', coerce=str) class TaskForm(FlaskForm): class TaskForm(FlaskForm): make = RadioField('Task', choices=list(tasks.items()), default='DFA', coerce=str) make = RadioField('Task', choices=list(tasks.items()), default='DFA', coerce=str) class ConvertForm(FlaskForm): class ConvertForm(FlaskForm): make = RadioField('Convert', choices=list(convs.items()), default='DFA', coerce=str) make = RadioField('Convert', choices=list(convs.items()), default='DFA', coerce=str) @bp.route('/compare', methods=('GET', 'POST')) @bp.route('/compare', methods=('GET', 'POST')) Loading @@ -50,7 +55,7 @@ def compare(): student_area = "" # areas remembers user input or replace it with examples student_area = "" # areas remembers user input or replace it with examples teacher_area = "" teacher_area = "" if request.method == 'POST' and 'submit_button' in request.form: # submit action if request.method == 'POST' and 'submit_button' in request.form: teacher_type = teacher_form.make.data teacher_type = teacher_form.make.data teacher_string = request.form['teacher_string'] teacher_string = request.form['teacher_string'] student_type = student_form.make.data student_type = student_form.make.data Loading @@ -59,35 +64,46 @@ def compare(): teacher_area = teacher_string teacher_area = teacher_string if student_string == "" or teacher_string == "": if student_string == "" or teacher_string == "": return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") checker = WebChecker(student_string=student_string, task=student_type) checker = WebChecker(student_string=student_string, task=student_type) result = checker.compare(teacher_string=teacher_string, teacher_type=teacher_type) result = checker.compare(teacher_string=teacher_string, teacher_type=teacher_type) if not isinstance(result, bool): if not isinstance(result, bool): return render_template('parsing_error.html') return render_template('parsing_error.html') extra_word_ce, missing_word_ce, inf = None, None, None extra_word_ce, missing_word_ce, inf = None, None, None if not result and checker.eq is not None: # languages aren't equivalent if not result and checker.eq is not None: # languages not equivalent extra_word_ce = checker.eq.left_counterexample extra_word_ce = checker.eq.left_counterexample missing_word_ce = checker.eq.right_counterexample missing_word_ce = checker.eq.right_counterexample inf = checker.eq.inf inf = checker.eq.inf return render_template('result_compare.html', compare=True, ok=result, return render_template('result_compare.html', compare=True, ok=result, inf=inf, inf=inf, task_solved=checker.task_solved, task_solved=checker.task_solved, alphabets=checker.alphabets, alphabets=checker.alphabets, extra_word_ce=extra_word_ce, missing_word_ce=missing_word_ce, extra_word_ce=extra_word_ce, is_task=checker.is_task, img_src=checker.img_src, langs=checker.languages, missing_word_ce=missing_word_ce, teacher=checker.teacher, student=checker.student, is_task=checker.is_task, teacher_type_string=types[checker.teacher.task], student_type_string=tasks[checker.student.task]) img_src=checker.img_src, langs=checker.languages, teacher=checker.teacher, student=checker.student, teacher_type_string=types[checker.teacher.task], student_type_string=tasks[checker.student.task]) if request.method == 'POST' and 'example_button' in request.form: if request.method == 'POST' and 'example_button' in request.form: teacher_type = teacher_form.make.data # of which types examples should be # of which types examples should be teacher_type = teacher_form.make.data student_type = student_form.make.data student_type = student_form.make.data if (teacher_type, student_type) in examples: if (teacher_type, student_type) in examples: teacher_area, student_area = examples[(teacher_type, student_type)] teacher_area, student_area = examples[(teacher_type, student_type)] return render_template('compare.html', student_form=student_form, teacher_form=teacher_form, return render_template('compare.html', student_area=student_area, teacher_area=teacher_area) student_form=student_form, teacher_form=teacher_form, student_area=student_area, teacher_area=teacher_area) # analogical to compare, only with just one input formalism # analogical to compare, only with just one input formalism Loading @@ -104,26 +120,32 @@ def convert(): student_area = student_string student_area = student_string if student_string == "": if student_string == "": return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") return render_template('parsing_error.html', error="Nebyl zadán vstupní formalismus.") checker = WebChecker(student_string=student_string, task=task) checker = WebChecker(student_string=student_string, task=task) try: try: output = checker.convert(student_type=student_type) output = checker.convert(student_type=student_type) except ParsingError as ex: except ParsingError: return render_template('parsing_error.html') return render_template('parsing_error.html') student = Language(string=student_string, task=student_type) student = Language(string=student_string, task=student_type) is_task = student.gen_is_task(task=task) is_task = student.gen_is_task(task=task) return render_template('result_convert.html', compare=False, student_string=student_string, return render_template('result_convert.html', compare=False, student_type=types[student_type], task=tasks[task], output=output, is_task=is_task) student_string=student_string, student_type=types[student_type], task=tasks[task], output=output, is_task=is_task) if request.method == 'POST' and 'example_button' in request.form: if request.method == 'POST' and 'example_button' in request.form: student_type = student_form.make.data student_type = student_form.make.data if student_type in convert_examples: if student_type in convert_examples: student_area = convert_examples[student_type] student_area = convert_examples[student_type] return render_template('convert.html', student_form=student_form, task_form=task_form, student_area=student_area) return render_template('convert.html', student_form=student_form, task_form=task_form, student_area=student_area) @bp.route('/userref') @bp.route('/userref') Loading
evalweb/examples.py +6 −5 Original line number Original line Diff line number Diff line Loading @@ -8,11 +8,12 @@ convert_examples: Dict[str, str] = {} teacher_dfa = "(0,a)=1 (1,b)=0 final={0}" teacher_dfa = "(0,a)=1 (1,b)=0 final={0}" student_dfa = "(A,a)=B (B,b)=C (C,a)=B final={A,C}" student_dfa = "(A,a)=B (B,b)=C (C,a)=B final={A,C}" teacher_dfa_total = parser.dfa_to_str(parser.str_to_dfa(teacher_dfa).total()) teacher_dfa_total = parser.dfa_to_str(parser.str_to_dfa(teacher_dfa).total()) teacher_efa = "(A,a)={B} (A,\e)={D} (B,b)={A} final={A,D}" teacher_efa = r"(A,a)={B} (A,\e)={D} (B,b)={A} final={A,D}" student_nfa = parser.nfa_to_str(parser.str_to_nfa(teacher_efa).eliminate_epsilon()) student_nfa = parser.nfa_to_str(parser.str_to_nfa(teacher_efa) student_gra = "S -> aS' | \e\nS' -> bA | b\nA -> aS'" .eliminate_epsilon()) student_gra = r"S -> aS' | \e\nS' -> bA | b\nA -> aS'" student_reg = "(ab)^*" student_reg = "(ab)^*" student_efa = "(A,a)={B} (A,\e)={D} (B,b)={C} (C,a)={B} final={C,D}" student_efa = r"(A,a)={B} (A,\e)={D} (B,b)={C} (C,a)={B} final={C,D}" examples[('DFA', 'DFA')] = (teacher_dfa, student_dfa) examples[('DFA', 'DFA')] = (teacher_dfa, student_dfa) examples[('DFA', 'TOT')] = (teacher_dfa, teacher_dfa_total) examples[('DFA', 'TOT')] = (teacher_dfa, teacher_dfa_total) Loading
evalweb/web_checker.py +42 −30 Original line number Original line Diff line number Diff line import lib.reg as reg import lib.reg as reg from lib.parsing.parser import Parser, ParsingError from lib.parsing.parser import Parser, ParsingError from lib.checker import transform, dfa_transform, nfa_transform, check_task, check_alphabets from lib.checker import transform, dfa_transform, nfa_transform, check_task, \ check_alphabets from typing import List, Tuple from typing import List, Tuple from enum import Enum from enum import Enum import enum import enum Loading @@ -14,7 +15,7 @@ class Size(Enum): class Language: # contains information about formalism and its language class Language: # contains information about formalism and its language def __init__(self, string: str, task: str = "DFA"): def __init__(self, string: str, task: str = "DFA") -> None: self.string = string self.string = string self.task = task self.task = task self.dfa = None self.dfa = None Loading @@ -24,7 +25,7 @@ class Language: # contains information about formalism and its language self.example = None self.example = None self.gen_lang_html() self.gen_lang_html() def gen_lang_html(self): def gen_lang_html(self) -> None: parser = Parser() parser = Parser() dfa = dfa_transform(self.string, self.task) dfa = dfa_transform(self.string, self.task) self.minimal = parser.dfa_to_str(dfa.minimize().canonize()) self.minimal = parser.dfa_to_str(dfa.minimize().canonize()) Loading Loading @@ -74,7 +75,8 @@ class WebChecker: try: try: teacher = Language(string=teacher_string, task=teacher_type) teacher = Language(string=teacher_string, task=teacher_type) student = Language(string=student_string, task=self.task) student = Language(string=student_string, task=self.task) student_solution = transform(student_string, task) # only for task checking # only for task checking student_solution = transform(student_string, task) except ParsingError as ex: # Parsing error, don't continue except ParsingError as ex: # Parsing error, don't continue return ex.args return ex.args Loading @@ -83,15 +85,18 @@ class WebChecker: self.student = student self.student = student self.is_task = teacher.gen_is_task(task=self.task) self.is_task = teacher.gen_is_task(task=self.task) if isinstance(student_solution, reg.DFA) or isinstance(student_solution, reg.NFA): if isinstance(student_solution, reg.DFA) \ or isinstance(student_solution, reg.NFA): self.task_solved = check_task(student_solution, task) self.task_solved = check_task(student_solution, task) if teacher.size == Size.Empty and student.size == Size.Empty: if teacher.size == Size.Empty and student.size == Size.Empty: return self.task_solved == "" return self.task_solved == "" # if the alphabets aren't same, languages aren't equal (unless they are both empty) # if the alphabets aren't same, languages aren't equal (unless they are # both empty) alphabets = check_alphabets(student_alpha=student.dfa.characters, alphabets = check_alphabets(student_alpha=student.dfa.characters, teacher_alpha=teacher.dfa.characters, task=task) teacher_alpha=teacher.dfa.characters, task=task) if alphabets != "": if alphabets != "": self.alphabets = alphabets self.alphabets = alphabets Loading @@ -99,26 +104,26 @@ class WebChecker: self.eq = reg.DFA.is_equivalent(student.dfa, teacher.dfa) self.eq = reg.DFA.is_equivalent(student.dfa, teacher.dfa) self.img_src = self.relation(self.eq.left_counterexample is None and self.img_src = self.relation(self.eq.left_counterexample is None self.eq.right_counterexample is None) and self.eq.right_counterexample is None) if self.task_solved == "" and \ if self.task_solved == "" and \ self.eq.right_counterexample is None and \ self.eq.right_counterexample is None and \ self.eq.left_counterexample is None: self.eq.left_counterexample is None: return True return True return False return False def compare(self, teacher_string: str, teacher_type: str): def compare(self, teacher_string: str, teacher_type: str): # signal.alarm(50) # from fja_checker: here would kill the web # signal.alarm(50) # from fja_checker: here would kill the web try: try: return self.dfa_task(teacher_type=teacher_type, teacher_string=teacher_string, return self.dfa_task(teacher_type=teacher_type, task=self.task, student_string=self.student_string) teacher_string=teacher_string, task=self.task, student_string=self.student_string) except ParsingError as ex: except ParsingError as ex: return ex.args return ex.args # raise ParsingError(ex.args) # raise ParsingError(ex.args) def convert(self, student_type): def convert(self, student_type): try: try: parser = Parser() parser = Parser() Loading @@ -141,10 +146,11 @@ class WebChecker: return parser.nfa_to_str(nfa) return parser.nfa_to_str(nfa) if self.task == "GRA": if self.task == "GRA": return parser.reggrammar_to_str(nfa.nfa_to_reggrammar().eliminate_useless()) return parser.reggrammar_to_str(nfa.nfa_to_reggrammar() .eliminate_useless()) except ParsingError as ex: except ParsingError as ex: return ex.args return ex.args # FIXME # raise ParsingError(ex.args) # raise ParsingError(ex.args) except Exception as ex: except Exception as ex: Loading @@ -155,7 +161,8 @@ class WebChecker: teacher = self.teacher.dfa teacher = self.teacher.dfa # language 0 on picture: complement of both # language 0 on picture: complement of both self.languages[0] = self.language((reg.DFA.union(teacher, student)).complement()) self.languages[0] = self.language( (reg.DFA.union(teacher, student)).complement()) if not eq: if not eq: if self.eq.left_counterexample is not None: # extra word if self.eq.left_counterexample is not None: # extra word Loading @@ -166,17 +173,22 @@ class WebChecker: self.languages[2] = self.student self.languages[2] = self.student return "disjunction" return "disjunction" else: else: self.languages[1] = self.language(reg.DFA.subtraction(teacher, student)) self.languages[1] = self.language(reg.DFA.subtraction( self.languages[2] = self.language(reg.DFA.subtraction(student, teacher)) teacher, student)) self.languages[3] = self.language(reg.DFA.intersection(teacher, student)) self.languages[2] = self.language(reg.DFA.subtraction( student, teacher)) self.languages[3] = self.language(reg.DFA.intersection( teacher, student)) return "intersection" return "intersection" else: # teacher is subset of student else: # teacher is subset of student self.languages[1] = self.teacher self.languages[1] = self.teacher self.languages[2] = self.language(reg.DFA.subtraction(student, teacher)) self.languages[2] = self.language(reg.DFA.subtraction( student, teacher)) picture = "t_in_s" picture = "t_in_s" else: # student is subset of teacher else: # student is subset of teacher self.languages[1] = self.language(reg.DFA.subtraction(teacher, student)) self.languages[1] = self.language(reg.DFA.subtraction( teacher, student)) self.languages[2] = self.student self.languages[2] = self.student picture = "s_in_t" picture = "s_in_t" Loading @@ -186,9 +198,11 @@ class WebChecker: self.languages[0] = self.language(teacher.complement()) self.languages[0] = self.language(teacher.complement()) self.languages[1] = self.teacher self.languages[1] = self.teacher #if self.teacher.size == Size.Empty or self.student.size == Size.Universal: # if self.teacher.size == Size.Empty \ # or self.student.size == Size.Universal: # picture += "_empty" # picture += "_empty" if self.teacher.size == Size.Universal or self.student.size == Size.Universal: if self.teacher.size == Size.Universal \ or self.student.size == Size.Universal: picture += "_universal" picture += "_universal" if self.teacher.size == Size.Universal: if self.teacher.size == Size.Universal: self.languages.pop(0) self.languages.pop(0) Loading @@ -202,7 +216,5 @@ class WebChecker: parser = Parser() parser = Parser() return Language(parser.dfa_to_str(dfa)) return Language(parser.dfa_to_str(dfa)) def DFA_lines(self, str): def DFA_lines(self, str_: str) -> None: pass pass