Работа с матрицами - Assembler (225810)

Узнай цену своей работы

Формулировка задачи:

Здравствуйте!!! В ассемблере, грубо говоря, я - чайник, поэтому прошу помощи у вас. У меня даны 3 квадратных матрицы различных размерностей. Для каждой из них необходимо определить сумму элементов последнего столбца и первой строки. Все полученные суммы нужно сложить и разделить на число, равное минимальному из размерностей матриц. Максимум, на что меня хватило - это на ввод матриц:
prg segment para public 'code'              ; заголовок сегмента
assume cs:prg,ds:prg,es:prg,ss:prg
                                            ; сообщим транслятору о намерении установить сегментные регистры
                                            ; cs, ds, es на наш сегмент
org 100h                                    ; место под PSP
beg: jmp start                              ; переход на start
mess_a db 0ah,0dh,'Vvedite razmer A : $'    ; приглашение для
                                            ; ввода размерности A
mess_b db 0ah,0dh,'Vvedite razmer B : $'    ; приглашение для
                                            ; ввода размерности B
mess_c db 0ah,0dh,'Vvedite razmer C : $'    ; приглашение для
                                            ; ввода размерности C                                           
mess_in_a db 0ah,0dh,'Vvedite elementi A: $' ; приглашение для
                                            ; ввода элементов матрицы A
mess_in_b db 0ah,0dh,'Vvedite elementi B: $' ; приглашение для
                                            ; ввода элементов матрицы B
mess_in_c db 0ah,0dh,'Vvedite elementi C: $' ; приглашение для
                                            ; ввода элементов матрицы C
gg db 0ah,0dh,'Itgovaja summa : $'
                                            
out_sr_a db 0ah,0dh,'Summa v A: $'
out_sr_b db 0ah,0dh,'Summa v B: $'
out_sr_c db 0ah,0dh,'Summa v C: $'
out_all_sred db 0ah,0dh,'Rezult = $'
                                            ; заголовок для вывода элементов массива
answer db 7 dup(?),'$'                      ; буфер под ответ
bufer db 0ah,0,11 dup(?)                    ; буфер для ввода
 
n_a dw ?                                    ; размерность матрицы A
n_b dw ?                                    ; размерность матрицы B
n_c dw ?                                    ; размерность матрицы C
 
matr_a dw 25 dup(?)                         ; память под матрицу A
matr_b dw 25 dup(?)                         ; память под матрицу B
matr_c dw 25 dup(?)                         ; память под матрицу C
 
sr_a dw ?                                   ; среднее в нечёт. столбцах матрицы А
sr_b dw ?                                   ; среднее в нечёт. столбцах матрицы B
sr_c dw ?                                   ; среднее в нечёт. столбцах матрицы C
i dw ?
all_sred dw ?
 
newline db 0ah,0dh,'$'                      ; для перевода строки
 
include bin2str.asm                         ; подключение процедуры bin2str, находящейся в файле
                                            ; bin2str.asm и осуществляющей преобразование числа в строку
                                            ; вход bin2str - ax - число;
                                            ; выход - строка по адресу ds:bx
include str2bin.asm                         ; подключение процедуры str2bin, находящейся в файле
                                            ; str2bin.asm и осуществляющей преобразование из строки в число
                                            ; вход str2bin - ds:bx - адрес строки
                                            ; выход - ax - число со знаком
                                            ; input – подпрограмма для ввода одного числа
                                            ; Вход: в dx - адрес буфера,
                                            ; Выход: в ax возвращается введенное число
input proc
    push bx                                     ; сохраним используемые регистры
    push dx
    push dx                                     ; сохраним адрес буфера, т.к. он
                                                ; будет запорчен при организации вывода строки newline
    lea dx,newline
    mov ah,09h
    int 21h                                     ;вывод строки
    pop dx                                      ; восстановим адрес буфера ввода
    mov ah,0ah                                  ;помещаем в ah номер прерывания
    int 21h                                     ;для ввода строки
    mov bx,dx                                   ;строка по адресу ds:dx
    inc bx                                      ;увеличиваем на 1 ee адрес
                                                ; и передаем его в процедуру str2bin
    call str2bin                                ;преобразуем строку в число
    pop dx                                      ;число будет в ax
    pop bx
    ret
input endp
                                                ; Процедура вывода числа, находящегося в ax
output proc
    push bx                                     ;сохраним используемый регистр
    lea bx,answer                               ;адрес буфера для преобразования
    call bin2str                                ;преобразуем число в строку
    lea dx,answer+1                             ;помещаем в dx адрес начала строки
    mov ah,09h                                  ;помещаем в ah номер прерывания
    int 21h                                     ;вывода строки
    lea dx,newline                              ;переход на новую строку
    mov ah,09h
    int 21h
    pop bx                                      ;восстановление bx
    ret
output endp
 
start: 
mov sr_a,0
mov sr_b,0
mov sr_c,0
mov all_sred,0
                    ;Ввод А
lea dx,mess_a                               ;Загружаем в dx адрес строки для ввода размера А
mov ah,09h                                  ;функция 09h – реализует вывод строки
int 21h                                     ;вызываем прерывание int 21h
lea dx,bufer                                ;загружаем в dx адрес буфера для ввода
call input                                  ;вызываем input
mov n_a,ax                                  ;сохраним введенное число в N для А
 
lea dx,mess_in_a                            ;Загружаем в dx адрес строки
mov ah,09h
int 21h                                     ;и выводим сообщение
mov cx,n_a                                  ;в cx запишем счетчик цикла по строкам(их колличество)
lea bx,matr_a                               ;в bx запишем адрес начала матрицы A
mov si,0                                    ;смещение от начала матрицы равно нулю
a1: 
    push cx                                 ;перед организацией цикла сохраним счетчик по строкам
    mov cx,n_a                              ; в cx запишем счетчик цикла по столбцам !!!%2!!!
    a2: 
        push cx                                     ; сохраним счетчик внутреннего цикла
        lea dx,bufer                                ; в dx адрес буфера для ввода
        call input                                  ; введем одно число (вернется в ax)
        mov [bx][si],ax                             ;и запишем его в матрицу A по
                                                    ; адресу (bx)+(si) с помощью базово-индексной адресации
        add si,2                                    ;переход к следующему элементу
        pop cx                                      ;восстановим счетчик цикла
    loop a2                                     ;продолжим цикл ввода элементов одной строки
    pop cx                                      ;восстановим счетчик внешнего цикла
loop a1                                     ;перейдем к следующей строке
 
                    ;Ввод B
                    
lea dx,mess_b                               ;Загружаем в dx адрес строки для ввода размера В
mov ah,09h                                  ;функция 09h – реализует вывод строки
int 21h                                     ;вызываем прерывание int 21h
lea dx,bufer                                ;загружаем в dx адрес буфера для ввода
call input                                  ;вызываем input
mov n_b,ax                                  ;сохраним введенное число в N для В
 
lea dx,mess_in_b                            ;Загружаем в dx адрес строки
mov ah,09h
int 21h                                     ;и выводим сообщение
mov cx,n_b                                  ;в cx запишем счетчик цикла по строкам(их колличество)
lea bx,matr_b                               ;в bx запишем адрес начала матрицы В
mov si,0                                    ;смещение от начала матрицы равно нулю
 
b1: 
    push cx                                 ;перед организацией цикла сохраним счетчик по строкам
    mov cx,n_b                              ; в cx запишем счетчик цикла по столбцам !!!%2!!!
    b2: 
        push cx                                     ; сохраним счетчик внутреннего цикла
        lea dx,bufer                                ; в dx адрес буфера для ввода
        call input                                  ; введем одно число (вернется в ax)
        mov [bx][si],ax                             ;и запишем его в матрицу В по
                                                    ; адресу (bx)+(si) с помощью базово-индексной адресации
        add si,2                                    ;переход к следующему элементу
        pop cx                                      ;восстановим счетчик цикла
    loop b2                                     ;продолжим цикл
    pop cx                                      ;восстановим счетчик внешнего цикла
loop b1                                     ;перейдем к следующей строке
 
                ;Ввод C
                    
lea dx,mess_c                               ;Загружаем в dx адрес строки для ввода размера С
mov ah,09h                                  ;функция 09h – реализует вывод строки
int 21h                                     ;вызываем прерывание int 21h
lea dx,bufer                                ;загружаем в dx адрес буфера для ввода
call input                                  ;вызываем input
mov n_c,ax                                  ;сохраним введенное число в N для С
 
lea dx,mess_in_c                            ;Загружаем в dx адрес строки 
mov ah,09h
int 21h                                     ;и выводим сообщение
mov cx,n_c                                  ;в cx запишем счетчик цикла по строкам(их колличество)
lea bx,matr_c                               ;в bx запишем адрес начала матрицы С
mov si,0                                    ;смещение от начала матрицы равно нулю
 
c1: 
    push cx                                 ;перед организацией цикла сохраним счетчик по строкам
    mov cx,n_c                              ; в cx запишем счетчик цикла по столбцам !!!%2!!!
    c2: 
        push cx                                     ; сохраним счетчик внутреннего цикла
        lea dx,bufer                                ; в dx адрес буфера для ввода
        call input                                  ; введем одно число (вернется в ax)
        mov [bx][si],ax                             ;и запишем его в матрицу С по
                                                    ; адресу (bx)+(si) с помощью базово-индексной адресации
        add si,2                                    ;переход к следующему элементу
        pop cx                                      ;восстановим счетчик цикла
    loop c2                                     ;продолжим цикл 
    pop cx                                      ;восстановим счетчик внешнего цикла
loop c1                                     ;перейдем к следующей строке
 
int 20h                                     ;завершить работу
prg ends                                    ;конец сегмента
end beg                                     ;точка входа - beg
Помогите пожалуйста с выполнением этого задания. Заранее спасибо!!!

Решение задачи: «Работа с матрицами»

textual
Листинг программы
matrix dw 5*5 dup (0)
element_size equ 2
str_size equ 5
.....
mov si, matrix
xor ax,ax
xor dx, dx
mov cx, str_size
@@:
    add ax, [si]
    adc dx, 0
    add si, element_size
    loop @b
 
mov cx, str_size-1
@@:
    add si, str_size*element_size
    add ax, [si]
    adc dx, 0
    loop @b
 
;ax=low(sum)
;dx=hi(sum)

Объяснение кода листинга программы

Код выполняет сложение элементов матрицы, начиная с первого элемента строки и сдвигаясь на элемент размером со строку до конца строки. Сумма элементов вычисляется в регистрах ax и dx. В конце вычисляется сумма матрицы, и её низкое значение сохраняется в ax, а высокое значение — в dx. Список действий:

  1. Задаются начальные значения переменных: — matrix — адрес матрицы; — element_size — размер элемента матрицы в байтах; — str_size — размер строки матрицы в элементах.
  2. Начинается выполнение цикла, который складывает элементы матрицы, начиная с первого элемента каждой строки: — В регистре cx устанавливается значение str_size; — В регистре si устанавливается адрес первого элемента текущей строки матрицы; — В регистре ax устанавливается значение 0, в регистре dx — значение 0; — Выполняется цикл, пока значение регистра cx больше или равно 0. При каждой итерации: — К значению в регистре ax прибавляется значение элемента матрицы, адрес которого находится в регистре si; — К значению в регистре dx прибавляется 0; — Регистр si увеличивается на элемент_size; — Уменьшается значение регистра cx на 1.
  3. Вычисляется сумма матрицы: — Устанавливается значение регистра cx равным str_size-1; — Регистр si устанавливается равным (str_size-1)*element_size плюс адрес первого элемента матрицы; — Выполняется цикл, пока значение регистра cx больше или равно 0. При каждой итерации: — К значению в регистре ax прибавляется значение элемента матрицы, адрес которого находится в регистре si; — К значению в регистре dx прибавляется 0; — Уменьшается значение регистра cx на 1.
  4. Результат вычисления суммы матрицы сохраняется в регистрах ax и dx.

Оцени полезность:

13   голосов , оценка 4.154 из 5