Форум программистов, компьютерный форум, киберфорум
Assembler для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.94/18: Рейтинг темы: голосов - 18, средняя оценка - 4.94
0 / 0 / 0
Регистрация: 11.05.2017
Сообщений: 13
1

Подсчитать количество нулевых и ненулевых элементов в заданном векторе

11.05.2017, 17:39. Показов 3173. Ответов 7
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Здравствуйте, не могу разобраться, как вводить знаковые числа в массив.Само задание такое:
Подсчитать количество нулевых и ненулевых элементов в заданном векторе и определить, каких элементов в векторе больше
а) элементы вектора однобайтовые;
б) элементы вектора двухбайтовые.

Вот, что получилось для двухбайтового массива
Кликните здесь для просмотра всего текста

Assembler
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
.model small
.stack 100h
.data
Mas dw 10 dup (?)
len dw 10
Sch_0 dw 0 ;счетчик нулевых элементов вектора
Sch_otr dw 0
msg_z db "Null"
msg_o db "Otr"
msg_ravn db "Ravny"
.code
InputInt proc 
 
    mov ah,0ah
    xor di,di
    mov dx,offset buff ; аддрес буфера
    int 21h ; принимаем строку
    mov dl,0ah
    mov ah,02
    int 21h ; выводим перевода строки
    
; обрабатываем содержимое буфера
    mov si,offset buff+2 ; берем аддрес начала строки
    cmp byte ptr [si],"-" ; если первый символ минус
     jnz ii1
    mov di,1  ; устанавливаем флаг
    inc si    ; и пропускаем его
ii1:
    xor ax,ax
    mov bx,10  ; основание сc
ii2:
    mov cl,[si] ; берем символ из буфера
    cmp cl,0dh  ; проверяем не последний ли он
    jz endin
    
; если символ не последний, то проверяем его на правильность
    cmp cl,'0'  ; если введен неверный символ <0
    jb er
    cmp cl,'9'  ; если введен неверный символ >9
    ja er
 
    sub cl,'0' ; делаем из символа число 
    mul bx     ; умножаем на 10
    add ax,cx  ; прибавляем к остальным
    inc si     ; указатель на следующий символ
    jmp ii2     ; повторяем
 
er:   ; если была ошибка, то выводим сообщение об этом и выходим
    mov dx, offset error
    mov ah,09
    int 21h
    int 20h
 
; все символы из буфера обработаны число находится в ax
endin:
    cmp di,1 ; если установлен флаг, то
    jnz ii3
    neg ax   ; делаем число отрицательным
ii3:
    ret
 
error db "incorrect number$"
buff    db 6,7 Dup(?)
InputInt endp
 
main proc
Mov cx, len ;инициализация счетчика цикла
Xor si,si ;инициализация индексного регистра
Cyc:call InputInt
mov mas[si],ax
inc si
dec cx
jz dal
jmp cyc
dal:Mov cx, len ;инициализация счетчика цикла
mov si,0
Xor si,si ;инициализация индексного регистра
Cycl: cmp mas[si],0 ;сравниваем элемент вектора с 0
Jz zero ;нуль-элементы считаем в блоке zero
Inc Sch_otr ;увеличиваем счетчик элементов <0
Jmp kon_cycl
Zero: Inc Sch_0 ;увеличиваем счетчик нулевых элементов
kon_cycl: inc si ;
loop cycl
mov ax, sch_otr
mov bx, sch_0
cmp ax,bx
jz ravn
Jg pol
mov ax,@data
    mov ds,ax
    mov ah,9
    mov dx,OFFSET msg_z
    int 21h
    mov ah,4ch
    int 21h
jmp konec
pol: mov ax,@data
    mov ds,ax
    mov ah,9
    mov dx,OFFSET msg_o
    int 21h
    mov ah,4ch
    int 21h
jmp konec
ravn: mov ax,@data
    mov ds,ax
    mov ah,9
    mov dx,OFFSET msg_ravn
    int 21h
    mov ah,4ch
    int 21h
konec: nop
main endp
end main
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
11.05.2017, 17:39
Ответы с готовыми решениями:

Найти произведение ненулевых элементов массива и подсчитать число нулевых элементов
Дан массив чисел c1,c2,...,c20,среди которых есть нулевые элементы. Найти произведение ненулевых...

В заданном векторе размерности N подсчитать количество компонент, принадлежащих отрезку
Ребят, помоги, пожалуйста!!! У меня 4 задачи, которые нужно решить на языке Visual Basic.Точно...

Составить функцию вычисляющую количество нулевых элементов в векторе
Заданы три вектора длиной n каждый. Составить функцию вычисляющую количество нулевых элементов в...

Подпрограммы: найти количество нулевых и количество ненулевых элементов массива
Найти величину n=ka1+ka2+kb1+kb2, где Ka1,ka2-количество нулевых и количество ненулевых элементов...

7
Модератор
Эксперт по электронике
8476 / 4335 / 1642
Регистрация: 01.02.2015
Сообщений: 13,461
Записей в блоге: 8
11.05.2017, 21:20 2
В чём проблема:
- совсем не получается ввести двухбайтовое целое со знаком
- просто число получается, но не получается заполнить массив

Добавлено через 6 минут
Возьмите следующий образец ввода числа из той же темы - к нему два примера вызова.

Ошибки у вас я вижу, но исправлять не очень хочу.
0
0 / 0 / 0
Регистрация: 11.05.2017
Сообщений: 13
12.05.2017, 23:22  [ТС] 3
Исправил. Вроде работает. Только один вопрос: почему для правильной работы нужно каждый раз заново ассемблировать и компилировать файл?
Кликните здесь для просмотра всего текста
Assembler
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
.model small
.stack 100h
.data
Mas dw 10 dup (?)
Sch_0 db 0 ;счетчик нулевых элементов вектора
Sch_otr db 0
msg_z db "Null", 13,10,'$' 
msg_o db "Otr", 13,10,'$'
.code
InputInt proc 
    mov ah,0ah
    xor di,di
    mov dx,offset buff ; аддрес буфера
    int 21h ; принимаем строку
    mov dl,0ah
    mov ah,02
    int 21h ; выводим перевода строки
    
; обрабатываем содержимое буфера
    mov si,offset buff+2 ; берем аддрес начала строки
    cmp byte ptr [si],"-" ; если первый символ минус
    jnz ii1
    mov di,1  ; устанавливаем флаг
    inc si    ; и пропускаем его
ii1:
    xor ax,ax
    mov bx,10  ; основание сc
ii2:
    mov cl,[si] ; берем символ из буфера
    cmp cl,0dh  ; проверяем не последний ли он
    jz endin
    
; если символ не последний, то проверяем его на правильность
    cmp cl,'0'  ; если введен неверный символ <0
    jb er
    cmp cl,'9'  ; если введен неверный символ >9
    ja er
 
    sub cl,'0' ; делаем из символа число 
    mul bx     ; умножаем на 10
    add ax,cx  ; прибавляем к остальным
    inc si     ; указатель на следующий символ
    jmp ii2     ; повторяем
 
er:   ; если была ошибка, то выводим сообщение об этом и выходим
    mov dx, offset error
    mov ah,09
    int 21h
    int 20h
 
; все символы из буфера обработаны число находится в ax
endin:
    cmp di,1 ; если установлен флаг, то
    jnz ii3
    neg ax   ; делаем число отрицательным
ii3:
    ret
 
error db "incorrect number$"
buff    db 6,7 Dup(?)
InputInt endp
 
main proc
Xor si,si ;инициализация индексного регистра
Mov cx, 10 ;инициализация счетчика цикла
cycl1:
push cx
call InputInt
mov mas[si], ax
inc si
pop cx
loop cycl1
Mov cx, 10 ;инициализация счетчика цикла
Xor si,si ;инициализация индексного регистра
Cycl: cmp mas[si],0 ;сравниваем элемент вектора с 0
Jz zero ;нуль-элементы считаем в блоке zero
Inc Sch_otr ;увеличиваем счетчик элементов <0
Jmp kon_cycl
Zero: Inc Sch_0 ;увеличиваем счетчик нулевых элементов
Jmp kon_cycl
kon_cycl: inc si ;переходим к следующему элементу
;вектора
loop cycl
mov ax,word ptr sch_0
mov bx,word ptr sch_otr
cmp ax,bx
Jl otrb
mov ax,@data
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_z
    int 21h
    mov ah,4ch
    int 21h
jmp konec
otrb:
mov ax,@data 
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_o
    int 21h
    mov ah,4ch
    int 21h
konec: mov ax,0
main endp
end main
0
Модератор
Эксперт по электронике
8476 / 4335 / 1642
Регистрация: 01.02.2015
Сообщений: 13,461
Записей в блоге: 8
12.05.2017, 23:41 4
Цитата Сообщение от Niobeus Посмотреть сообщение
почему для правильной работы нужно каждый раз заново ассемблировать и компилировать файл?
Зачем? У вас же создаётся исполняемый файл *.exe.
Могу лишь предположить, что вы работаете в DOSBox. И этот DOSBox своеобразно настроен.

Добавлено через 3 минуты
--------
Ничего вы не исправили.
Для DOS exe иная структура программы. https://www.cyberforum.ru/post9602973.html
0
0 / 0 / 0
Регистрация: 11.05.2017
Сообщений: 13
13.05.2017, 10:50  [ТС] 5
Вот другая программа без ввода чисел. Она работает (проверил несколько раз).
Кликните здесь для просмотра всего текста
Assembler
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
.model small
.stack 100h
.data
 
Mas dw 1, 0, 0, 0, 0, 0, -9, 0, -7, 9
Sch_0 dw 0 ;счетчик нулевых элементов вектора
Sch_otr dw 0
 
msg_z db "Null", 13,10,'$' 
msg_o db "Otr", 13,10,'$'
 
.code
 
main:
mov ax, @data
mov ds, ax
xor ax,ax
Mov cx, 10 ;инициализация счетчика цикла
Xor si,si ;инициализация индексного регистра
 
Cycl: cmp mas[si],0 ;сравниваем элемент вектора с 0
Jz zero ;нуль-элементы считаем в блоке zero
jl otr
jmp kon_cycl
otr:Inc Sch_otr ;увеличиваем счетчик элементов <0
Jmp kon_cycl
Zero: Inc Sch_0 ;увеличиваем счетчик нулевых элементов
kon_cycl: inc si ;переходим к следующему элементу
;вектора
loop cycl
 
mov bx, sch_0
mov ax, sch_otr
cmp ax,bx
Jg otrb
mov ax,@data
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_z
    int 21h
    mov ah,4ch
    int 21h
jmp konec
otrb:
mov ax,@data 
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_o
    int 21h
    mov ah,4ch
    int 21h
konec:
end main


Почему, когда я вставляю ввод чисел, программа не хочет работать?
Кликните здесь для просмотра всего текста
Assembler
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
.model small
.stack 100h
.data
 
Mas dw 10 dup (?)
Sch_0 dw 0 ;счетчик нулевых элементов вектора
Sch_otr dw 0
 
msg_z db "Null", 13,10,'$' 
msg_o db "Otr", 13,10,'$'
 
.code
jmp main
InputInt proc 
    mov ah,0ah
    xor di,di
    mov dx,offset buff ; аддрес буфера
    int 21h ; принимаем строку
    mov dl,0ah
    mov ah,02
    int 21h ; выводим перевода строки
    
; обрабатываем содержимое буфера
    mov si,offset buff+2 ; берем аддрес начала строки
    cmp byte ptr [si],"-" ; если первый символ минус
    jnz ii1
    mov di,1  ; устанавливаем флаг
    inc si    ; и пропускаем его
ii1:
    xor ax,ax
    mov bx,10  ; основание сc
ii2:
    mov cl,[si] ; берем символ из буфера
    cmp cl,0dh  ; проверяем не последний ли он
    jz endin
 
    sub cl,'0' ; делаем из символа число 
    mul bx     ; умножаем на 10
    add ax,cx  ; прибавляем к остальным
    inc si     ; указатель на следующий символ
    jmp ii2     ; повторяем
 
; все символы из буфера обработаны число находится в ax
endin:
    cmp di,1 ; если установлен флаг, то
    jnz ii3
    neg ax   ; делаем число отрицательным
ii3:
    ret
 
buff    db 6,7 Dup(?)
InputInt endp
 
main:
mov ax, @data
mov ds, ax
xor ax,ax
Xor si,si ;инициализация индексного регистра
Mov cx, 10 ;инициализация счетчика цикла
 
cycl1:
push cx
call InputInt
mov mas[si], ax
inc si
pop cx
loop cycl1
 
xor ax,ax
Mov cx, 10 ;инициализация счетчика цикла
Xor si,si ;инициализация индексного регистра
 
Cycl: cmp mas[si],0 ;сравниваем элемент вектора с 0
Jz zero ;нуль-элементы считаем в блоке zero
jl otr
jmp kon_cycl
otr:Inc Sch_otr ;увеличиваем счетчик элементов <0
Jmp kon_cycl
Zero: Inc Sch_0 ;увеличиваем счетчик нулевых элементов
kon_cycl: inc si ;переходим к следующему элементу
;вектора
loop cycl
 
mov bx, sch_0
mov ax, sch_otr
cmp ax,bx
Jg otrb
mov ax,@data
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_z
    int 21h
    mov ah,4ch
    int 21h
jmp konec
otrb:
mov ax,@data 
    mov ds,ax
    mov ah,9
mov dx,OFFSET msg_o
    int 21h
    mov ah,4ch
    int 21h
konec:
end main
0
593 / 390 / 70
Регистрация: 29.03.2013
Сообщений: 813
13.05.2017, 13:48 6
Niobeus, Может быть от того, что буфер для ввода ты сделал в сегменте кода, а не данных. А может не только из-за этого.
0
0 / 0 / 0
Регистрация: 11.05.2017
Сообщений: 13
13.05.2017, 15:41  [ТС] 7
Argogo, не из-за этого. Похоже, что счетчик Sch_0 всегда больше Sch_otr. А из-за чего так произошло, я не знаю
0
593 / 390 / 70
Регистрация: 29.03.2013
Сообщений: 813
13.05.2017, 16:27 8
Цитата Сообщение от Niobeus Посмотреть сообщение
Argogo, не из-за этого.
Из-за этого программа получает не введённые тобой числа, а случайный мусор.

Далее, в строке 64 ты сохраняешь слово, а в строке 65 увеличиваешь указатель на 1. Внимание, вопрос: к чему это приведёт? Можешь не отвечать на него, пока не исправишь ошибку, на которую я указал в предыдущем посте.
1
13.05.2017, 16:27
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
13.05.2017, 16:27
Помогаю со студенческими работами здесь

В целочисленном векторе определить количество положительных, отрицательных и нулевых элементов
В целочисленном векторе vectorn определить количество положительных, отрицательных и нулевых...

Найти произведение ненулевых элементов и количество нулевых элементов одномерного массива
Здравствуйте! Помогите, пожалуйста, сделать программу в Лазарусе 1. Дан одномерный массив. Найти...

Найти произведение ненулевых элементов и количество нулевых элементов массива
Дан одномерный массив. Найти произведение ненулевых элементов и количество нулевых элементов. ...

Найти произведение ненулевых элементов и количество нулевых элементов
дан вектор Х (20).найти произведение ненулевых элементов и количество нулевых элементов


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
8
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru