我不明白我在哪里犯了错误。这是问题的情况(我通过翻译器运行了所有内容,因此可能存在一些小错误):
Мы хотим создать простой интерпретатор ассемблера, который будет поддерживать следующие инструкции:
- mov x y - копирует y(либо постоянное значение, либо содержимое регистра) в регистр x
- inc x - увеличивает содержимое реестра x на единицу
- dec x - уменьшает содержимое регистра x на единицу
- jnz x y - переходит к инструкции y на шаг вперед (положительное значение означает вперед, отрицательное означает назад, y может быть регистром или константой), но только если x(константа или регистр) не равна нулю
Имена регистров указываются в алфавитном порядке (только буквы). Константы всегда являются
целыми числами (положительными или отрицательными).
Примечание: jnz инструкция перемещается относительно самой себя. Например, смещение -1 будет
продолжаться с предыдущей инструкции, а смещение 2 будет пропускать следующую инструкцию.
Функция примет входной список с последовательностью инструкций программы и выполнит их.
Программа завершается, когда больше нет инструкций для выполнения, и возвращает словарь
(таблицу в COBOL) с содержимым регистров.
Кроме того, каждому inc// в регистре всегда будет предшествовать a в регистре, поэтому вам
не нужно беспокоиться о неинициализированных регистрах dec jnz mov.
例子:
["mov a 5"; "inc a"; "dec a"; "dec a"; "jnz a -1"; "inc a"]
visualized:
mov a 5
inc a
dec a
dec a
jnz a -1
inc a
上面的代码换句话说:
установите a для регистрации значение 5,
увеличить его стоимость на 1,
уменьшить его значение на 2,
затем уменьшайте его значение, пока оно не станет равным нулю ( jnz a -1 переход к предыдущей инструкции, если a оно не равно нулю)
а затем увеличить его значение на 1, оставив регистр a равным 1
该函数应该返回:
{'a': 1}
我的决定:
class Interpreter:
counter = 0
program = None
def __init__(self):
self.regs = {}
def mov(self, val_1: str, val_2: str):
if val_2.isalpha():
val_2 = self.regs[val_2]
self.regs[val_1] = int(val_2)
def inc(self, reg: str):
self.regs[reg] += 1
def dec(self, reg: str):
self.regs[reg] -= 1
def simple_assembler(program):
len_ = len(program)
ex = Interpreter()
Interpreter.program = program
while Interpreter.counter < len_:
spl = Interpreter.program[Interpreter.counter].split()
try:
controller(spl[0], spl[1], spl[2], ex=ex)
except IndexError:
controller(spl[0], spl[1], ex=ex)
Interpreter.counter = 0
Interpreter.program = None
return ex.regs
def controller(instruction, val_1, val_2=None, ex=None):
if not val_2:
match instruction:
case 'inc':
ex.inc(val_1)
case 'dec':
ex.dec(val_1)
else:
match instruction:
case 'mov':
ex.mov(val_1, val_2)
case 'jnz':
if val_1.isalpha():
val = val_1
if ex.regs[val] <= 0:
Interpreter.counter += 1
return
else:
val = int(val_1)
if val <= 0:
Interpreter.counter += 1
return
if val_2.isalpha():
step = ex.regs[val_2]
else:
step = int(val_2)
next_instruction = Interpreter.program[Interpreter.counter + step].split()[0]
controller(instruction=next_instruction, val_1=val, ex=ex)
Interpreter.counter = Interpreter.counter + step
return
Interpreter.counter += 1
# первая тестовая строка, тут все ок, при ее передаче в simple_assembler() ответ должен быть: {'a': 1}
s1 = '''\
mov a 5
inc a
dec a
dec a
jnz a -1
inc a'''
# вторая и последняя тестовая строка из базовых тестов, у меня получается ответ:
# {'c': 12863, 'b': 12863, 'a': 12863}, а правильный: {'a': 409600, 'c': 409600, 'b': 409600}
s2 = '''\
mov c 12
mov b 0
mov a 200
dec a
inc b
jnz a -2
dec c
mov a b
jnz c -5
jnz 0 1
mov c a'''
# print(simple_assembler(s1.splitlines()))
print(simple_assembler(s2.splitlines()))
我想了解我做错了什么:我是否误解了某些指令的逻辑?例如,jnz x y据我了解,它必须根据符号将执行“指针”抛出y步骤,并选择位于结果位置的指令x(如果数量有限)x != 0或它的内容(如果x它是有限的)。是一个寄存器。此后,指令是否也按顺序进行,还是控制直接返回jnz?



