Задать вопрос
@nazariy228

Где ошибка в коде?

uint16_t program[] = {
    /* Ввод числа */
    /*mem[0x3000]=*/   0xF020,    // TRAP x20           ; Считать символ с клавиатуры в R0
    /*mem[0x3001]=*/   0xF021,    // TRAP x21           ; Эхо символа на консоль (опционально)
    /*mem[0x3002]=*/   0x5020,    // AND R0, R0, #0x0F  ; Конвертировать ASCII в число
    /*mem[0x3003]=*/   0x5000,    // AND R1, R1, #0     ; Очистить R1 для введённого числа
    /*mem[0x3004]=*/   0x1020,    // ADD R1, R0, #0     ; Скопировать введённое число в R1

    /* Инициализация делителя в R2 и флага простоты в R4 */
    /*mem[0x3005]=*/   0x5060,    // AND R2, R2, #0     ; Очистить R2 для делителя
    /*mem[0x3006]=*/   0x1022,    // ADD R2, R2, #2     ; Установить R2 = 2 (начальный делитель)
    /*mem[0x3007]=*/   0x5460,    // AND R4, R4, #0     ; Очистить R4 для флага простоты
    /*mem[0x3008]=*/   0x1461,    // ADD R4, R4, #1     ; Установить R4 = 1 (считаем простым до доказательства обратного)

    /* Проверка: если R1 < 2, то число не простое */
    /*mem[0x3009]=*/   0x1021,    // ADD R1, R1, #-1    ; Проверить, если R1 < 2
    /*mem[0x300A]=*/   0x0E06,    // BRn NOT_PRIME      ; Если R1 < 2, перейти к NOT_PRIME
    /*mem[0x300B]=*/   0x1020,    // ADD R1, R1, #1     ; Восстановить R1 (R1 >= 2)

    /* Начало цикла проверки простоты */
    /*mem[0x300C]=*/   0x5280,    // ADD R3, R2, #0     ; Скопировать R2 в R3 (текущий делитель)
    /*mem[0x300D]=*/   0x5400,    // AND R4, R4, #1     ; Установить R4 = 1 (предполагаем, что число простое)

    /*mem[0x300E]=*/   0x9463,    // NOT R3, R3         ; Задать R3 = -R2 (для вычитания)
    /*mem[0x300F]=*/   0x1C83,    // ADD R4, R4, R3     ; Вычесть R2 из R4 (проверить делимость)
    /*mem[0x3010]=*/   0x1022,    // ADD R4, R4, R2     ; Если остаток 0, значит число не простое
    /*mem[0x3011]=*/   0x0E03,    // BRz NOT_PRIME      ; Если R4 == 0, перейти к NOT_PRIME
    /*mem[0x3012]=*/   0x1A20,    // ADD R2, R2, #1     ; Увеличить делитель на 1
    /*mem[0x3013]=*/   0x1C21,    // ADD R3, R2, #0     ; Скопировать R2 в R3 для проверки конца цикла
    /*mem[0x3014]=*/   0x1C83,    // ADD R4, R1, R3     ; Если делитель > корня R1, выход из цикла

    /* Повторение цикла */
    /*mem[0x3015]=*/   0x0FEA,    // BR LOOP_START      ; Вернуться к началу цикла для следующего делителя

    /* Если число является простым */
    /*mem[0x3016]=*/   0x5001,    // ADD R0, R0, #1     ; Установить R0 = 1 (простое число)
    /*mem[0x3017]=*/   0xF021,    // TRAP x21           ; Вывести 1
    /*mem[0x3018]=*/   0xF025,    // HALT               ; Остановить программу

    /* Если число не является простым */
    /*mem[0x3019]=*/   0x5000,    // AND R0, R0, #0     ; Установить R0 = 0 (не простое)
    /*mem[0x301A]=*/   0xF021,    // TRAP x21           ; Вывести 0
    /*mem[0x301B]=*/   0xF025,    // HALT               ; Остановить программу
};

Программа зациклилась, ввожу значение в консоль, оно в ответ дублирует его, где ошибка?
  • Вопрос задан
  • 257 просмотров
Подписаться 2 Простой 2 комментария
Помогут разобраться в теме Все курсы
  • Яндекс Практикум
    Разработчик C++
    9 месяцев
    Далее
  • Яндекс Практикум
    Разработчик C++ расширенный
    12 месяцев
    Далее
  • Яндекс Практикум
    Мидл разработчик С++
    4 месяца
    Далее
Пригласить эксперта
Ответы на вопрос 1
@AlexandrBrown
И такс начнем:

В строках 0x300E, 0x300F и 0x3010 программа использует сложение и отрицание для проверки остатка. Вместо этого попробуй использовать команду MOD или корректную операцию для деления, чтобы проще вычислять остаток.
Убедсь, что после вычитания в R4 действительно остаётся 0, если число делится без остатка.
Условия выхода из цикла:
В строке 0x3014 (команда ADD R4, R1, R3) происходит проверка делителя на превышение корня числа R1. Здесь может возникнуть ошибка: после увеличения R2, R3 следует проверить, не достиг ли он значения, превышающего половину R1. Если это так, программа должна выйти из цикла.

Использование метки для выхода:

Команда BR LOOP_START (строка 0x3015) ведёт обратно в начало цикла, даже если число уже определено как простое или составное. Чтобы выйти из цикла в случае определения, что число не простое, замени её на условный переход к меткам PRIME или NOT_PRIME.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы