IPB
ЛогинПароль:

> ПРАВИЛА РАЗДЕЛА!!!

1. Заголовок или название темы должно быть информативным
2. Все тексты программ должны помещаться в теги [CODE=asm] [/CODE]
3. Прежде чем задавать вопрос, см. "FAQ",если там не нашли ответа, воспользуйтесь ПОИСКОМ, возможно, такую задачу уже решали!
4. Не предлагайте свои решения на других языках, кроме Ассемблера. Исключение только с согласия модератора.
5. НЕ используйте форум для личного общения! Все, что не относиться к обсуждению темы - на PM!
6. Проверяйте программы перед тем, как выложить их на форум!!

 
 Ответить  Открыть новую тему 
> Заполнение матрицы случайными числами
сообщение
Сообщение #1


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Объясните пожалуйста, как можно инициализировать матрицу случайными числами??
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #2


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


вот что у меня получилось...только матрица инициализируется совершенно различными символами, а хотелось бы, чтобы только числами..Объясните пожалуста, как это сделать?

assume CS: code, DS: data
code segment
begin:

	mov AX, data
	mov DS, AX
	
	;xor ax,ax
	mov cx,3
	mov si,0
	mov bx,0
external:
	push cx
	mov cx,3
	mov si,0
iternal:
	xor ax,ax
	out 43h,al
	in al,40h
	;mov bh,i
	mov array[bx][si],al
	;inc i
	inc si
	loop iternal
	pop cx
	inc bx
	loop external
	
	
	mov cx,3
	mov si,0
	mov bx,0
	
exshow:
	push cx
	mov cx,3
	mov si,0
ishow:
	mov ah,02h
	mov dl,array[bx][si]
	;add dl,30h  у меня символы!
	int 21h
	inc si
loop ishow
	lea dx,nl           ;переход на новую строку
	pop cx
	inc bx
loop exshow
		
exit:
	mov ah,08h
	int 21h
	mov ax,4c00h
	int 21h
	
	
code ends

data segment
	array db 3 dup(3 dup(?))
	i db 0
	nl db 13,10,'$'
data ends

stk segment stack
	dw 128 dup (0)
stk ends

end begin


и ещё не срабатывает переход на следующую строку при выводе матрицы..
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #3


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


1. Я уже навскидку не помню, 40/43 - это порты таймера? Если "да", то алгоритм получения случайного числа принципиально неверный. Он подходит либо для получения ОДНОГО случайного числа, либо инициализации ДПСЧ, но никак не для получения серии случайных чисел.
2. Что хранится у тебя в массиве: числа или символы? Если числа, то это одно - тогда у тебя в массиве то, что надо, но при выводе на экран их надо преобразовывать в числа от 0 до 255. Если же - символы, причем требуется, чтобы символы были цифрами (не числами), то необходимо дополнительное преобразование для приведения символов к нужному диапазону, т.е. к 30h-39h.
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #4


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Цитата(andriano @ 13.05.2008 19:42) *

1. Я уже навскидку не помню, 40/43 - это порты таймера? Если "да", то алгоритм получения случайного числа принципиально неверный. Он подходит либо для получения ОДНОГО случайного числа, либо инициализации ДПСЧ, но никак не для получения серии случайных чисел.
2. Что хранится у тебя в массиве: числа или символы? Если числа, то это одно - тогда у тебя в массиве то, что надо, но при выводе на экран их надо преобразовывать в числа от 0 до 255. Если же - символы, причем требуется, чтобы символы были цифрами (не числами), то необходимо дополнительное преобразование для приведения символов к нужному диапазону, т.е. к 30h-39h.

1. насколько я поняла, да - это порты таймера..
2.
array db 3 dup(3 dup(?))

в матрице символы.. а как вообще нужно преобразовывать к нужному диапазону?

Сообщение отредактировано: 18192123 -
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #5


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


1. Тогда у тебя последовательность явно не случайных чисел.
2. Например, делением на 26 (частное) или на 10 (остаток) с последующим прибавлением 30h, т.е. кода символа "0".
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #6


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Цитата(andriano @ 13.05.2008 20:20) *

1. Тогда у тебя последовательность явно не случайных чисел.

т.е мне нужно использовать другие порты?
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #7


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


Нет. В IBM PC нет встроенного датчиа случайных чисел, поэтому пытаться извлечь их откуда-то - задача не из простых.
Обычно вместо случайных чисел используют псевдослучайные - т.е. вполне конкретную циклическую последовательность чисел, формируемых по определенному алгоритму, которая по статистическим характеристикам близка к последовательности случайных чисел.
Но т.к. числа формируются алгоритмически, последовательность их жестко предопределена. Чтобы избавиться от этой предопределенности вводят дополнительную процедуру инициализации алгоритма, при которой та же самая циклическая последовательность уже будет начинаться не с первого члена, а с какого-то другого. Т.е. при разных запусках программы последовательность не будет повторяться, а будет каждый раз другая. Для инициализации обычно берут текущее время.
Т.е. порядок работы такой (примеры, извини, в Паскаль - оболочке):
пишем сам генератор ПСЧ (простой и быстрый, но не уверен, что пройдет все статистические тесты):
var iax,ibx:word;

function random:word;{ »poµeñπpa óδñaτ¿ äBôX 16-í¿Γ¡δx »ceóño-c½πτa¡δx τ¿ce½:}
var q:word;
begin
   asm
       mov ax,iax
       mov bx,ibx
       xor  ax,bx
       shl  ax,1
       adc  bx,0
       xor  bx,ax
       xchg bl,bh
       mov iax,ax
       mov ibx,bx
   end
   random := ibx;
end;
где в переменных хранится текущее состояние ДПСЧ.
Эти переменные надо инициализировать. Вот это можно сделать при помощи таймера:
procedure randomize;
begin
   asm
       Mov  AL,00000000b
       Out  43h,AL
       In   AL,40h
       Mov  AH,AL
       In   AL,40h
       XChg AL,AH
       mov iax,ax
   end
  ibx := 9821;
end;

Теперь перед первым использованием мы вызываем randomize, а затем используем random
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #8


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Вот к чему я пришла..генерацию вставила, но программа зацикливается..(вообще программа выводит 10 раз матрицу, заполненную случайными числами и ждёт нажатия клавиши)


dely    macro time; (1)
        local zd,c1,cikl,ii,ii1; (2) описываем все метки, используемые вмакроопределении
        push cx; (3)помещаем в стек используемые в макроопределении регистры
        push bx; (4)
        push bp; (5)
        push ax; (6)
        push dx; (7)
        mov cx,time; (8) задаём количество повторений цикла задержки zd – задержка в цикле 18.2 секунды
zd:     push cx; (9)
        mov bp,0;(10)
        mov bx,1;(11)
        
cikl:   
        inc BP;(12)
        mov ah,00h;(13)       
        int 1Ah;(14)
        cmp BP,1;(15)
        je ii;(16) переходим на метку ii на первой итерации цикла
        jmp ii1;(17) на следующих итерациях переходим на метку ii1
ii:     add bx,dx;(18) формируем значение на единицу больше, чем в регистре dx
ii1:                    ; (19)
        cmp bx,dx;(20) если значение в регистре dx изменилось(сравниваем значение в dx с сформированным в строке 18 значением в регистре bx, которое на единицу больше, на единицу больше значение в dx станет через 18.2 сек)
        jne cikl;(21) если нет, то новая итерация цикла
        pop cx;(22) если да, конец макрокоманды задержки
        loop zd;(23)
        pop cx;(24)
        pop bx;(25)
        pop bp;(26)
        pop ax;(27)
        pop dx;(28)
        endm;(29)

assume CS: code, DS: data
code segment
randomize proc
	Mov  AL,00000000b
	Out  43h,AL
	In   AL,40h
	Mov  AH,AL
	In   AL,40h
	XChg AL,AH
    mov iax,ax

randomize endp

matr proc
	mov cx,3
	mov si,0
	mov bx,0
	call randomize
external:
	push cx
	mov cx,3
	mov si,0
iternal:
	
	mov ax,iax
	mov bx,ibx
	xor  ax,bx
	shl  ax,1
	adc  bx,0
	xor  bx,ax
	xchg bl,bh
	mov iax,ax
	mov ibx,bx

	mov array[bx][si],ax
	add si,2
	loop iternal
	pop cx
	add bx,4
	loop external
	
	
	mov cx,3
	mov si,0
	mov bx,0
exshow:
	push cx
	mov cx,3
	mov si,0
ishow:
	mov ah,02h
	mov dx,array[bx][si]
	add dl,30h  
	int 21h
	add si,2
loop ishow
	;lea dx,nl           ;переход на новую строку
	pop cx
	add bx,4
loop exshow
	ret
matr endp	

begin:

	mov AX, data
	mov DS, AX
	mov cx,10
miganie:
	push cx
	call matr
	dely 18
	mov ah,02h ;сдвижка курсора обратно в начало строки
	mov bh,00
	mov dh,15
	mov dl,0
	int 10h
	pop cx
	loop miganie
	
exit:
	mov ah,08h
	int 21h
	mov ax,4c00h
	int 21h
	
	
code ends

data segment
	array dw 3 dup(3 dup(0))
	i db 0
	nl db 13,10,'$'
	iax dw 0
	ibx dw 9821
data ends

stk segment stack
	dw 128 dup (1)
stk ends

end begin



 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #9


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


Ты пытаешься использовать регистр bx сразу для двух целей: участие в генерации ПСЧ и для адресации в массиве. Естественно, его содержимое при этом портится. Ты уж либо сохраняй его содержимое в стеке (кстати, посмотри, нельзя ли вместно него использовать dx), либо, что лучше, вынеси генерацию ПСЧ в отдельную процедуру с сохранением регистров.
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #10


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Я вынесла генерацию ПСЧ в отдельную процедуру (значение регистра bx сохраняется в стеке перед её вызовом)..Но программа по-прежнему не работает..Объясните пожалуста, в чём дело?


dely    macro time; (1)
        local zd,c1,cikl,ii,ii1; (2) описываем все метки, используемые вмакроопределении
        push cx; (3)помещаем в стек используемые в макроопределении регистры
        push bx; (4)
        push bp; (5)
        push ax; (6)
        push dx; (7)
        mov cx,time; (8) задаём количество повторений цикла задержки zd – задержка в цикле 18.2 секунды
zd:     push cx; (9)
        mov bp,0;(10)
        mov bx,1;(11)
        
cikl:   
        inc BP;(12)
        mov ah,00h;(13)       
        int 1Ah;(14)
        cmp BP,1;(15)
        je ii;(16) переходим на метку ii на первой итерации цикла
        jmp ii1;(17) на следующих итерациях переходим на метку ii1
ii:     add bx,dx;(18) формируем значение на единицу больше, чем в регистре dx
ii1:                    ; (19)
        cmp bx,dx;(20) если значение в регистре dx изменилось(сравниваем значение в dx с сформированным в строке 18 значением в регистре bx, которое на единицу больше, на единицу больше значение в dx станет через 18.2 сек)
        jne cikl;(21) если нет, то новая итерация цикла
        pop cx;(22) если да, конец макрокоманды задержки
        loop zd;(23)
        pop cx;(24)
        pop bx;(25)
        pop bp;(26)
        pop ax;(27)
        pop dx;(28)
        endm;(29)

assume CS: code, DS: data
code segment
randomize proc
	Mov  AL,00000000b
	Out  43h,AL
	In   AL,40h
	Mov  AH,AL
	In   AL,40h
	XChg AL,AH
    mov iax,ax
randomize endp

random proc
	mov ax,iax
	mov bx,ibx
	xor  ax,bx
	shl  ax,1
	adc  bx,0
	xor  bx,ax
	xchg bl,bh
	mov iax,ax
	mov ibx,bx
random endp

matr proc
	mov cx,3
	mov si,0
	mov bx,0
	
	call randomize
	
external:
	push cx
	mov cx,3
	mov si,0
	
iternal:
	push bx
	call random	
	pop bx
	mov array[bx][si],ax
	add si,2
	loop iternal
	pop cx
	add bx,4
	loop external
	
	mov cx,3
	mov si,0
	mov bx,0
exshow:
	push cx
	mov cx,3
	mov si,0
ishow:
	mov ah,02h
	mov dx,array[bx][si]
	add dl,30h  
	int 21h
	add si,2
loop ishow
	;lea dx,nl           ;переход на новую строку
	pop cx
	add bx,4
loop exshow
	ret
matr endp	

begin:

	mov AX, data
	mov DS, AX
	mov cx,10
miganie:
	push cx
	call matr
	dely 18
	mov ah,02h ;сдвижка курсора обратно в начало строки
	mov bh,00
	mov dh,15
	mov dl,0
	int 10h
	pop cx
	loop miganie
	
exit:
	mov ah,08h
	int 21h
	mov ax,4c00h
	int 21h
	
	
code ends

data segment
	array dw 3 dup(3 dup(0))
	i db 0
	nl db 13,10,'$'
	iax dw 0
	ibx dw 9821
data ends

stk segment stack
	dw 128 dup (1)
stk ends

end begin


 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #11


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


1. Вместо "не работает" хотелось бы узнать конкретные симптомы, по которым ты определяешь отсутствие работоспособности. Тем более, что у меня сейчас нет ни одного установленного Ассемблера, следовательно, проверить никак не могу - могу лишь полагаться на твои слова.

2. push/pop принято помещать внутри процедуры. Т.е. те регистры, которые процедура портит, она и должна сохранять, а вызывающая программа об этом ничего знать не обязана.

3. si ты увеличиваешь 3 раза по 2, после чего si возвращаешь в 0, а bx увеличиваешь лишь на 4. Т.е. пишешь в то место, которое было заполнено на предыдущем проходе. У тебя какие размеры массива? Обычно их указывают как именованную константу в дальнейшем уже прибавляют к регистру константу по имени, а не конкретное число. Так проще и отлаживать и изменять программу, если в дальнейшем потребуется.
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #12


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Цитата(andriano @ 17.05.2008 18:30) *

1. Вместо "не работает" хотелось бы узнать конкретные симптомы, по которым ты определяешь отсутствие работоспособности. Тем более, что у меня сейчас нет ни одного установленного Ассемблера, следовательно, проверить никак не могу - могу лишь полагаться на твои слова.

2. push/pop принято помещать внутри процедуры. Т.е. те регистры, которые процедура портит, она и должна сохранять, а вызывающая программа об этом ничего знать не обязана.

3. si ты увеличиваешь 3 раза по 2, после чего si возвращаешь в 0, а bx увеличиваешь лишь на 4. Т.е. пишешь в то место, которое было заполнено на предыдущем проходе. У тебя какие размеры массива? Обычно их указывают как именованную константу в дальнейшем уже прибавляют к регистру константу по имени, а не конкретное число. Так проще и отлаживать и изменять программу, если в дальнейшем потребуется.

1. курсорчик мигает на одном и том же месте (начало 15-й строчки), ничего не выводится, предусмотренный выход по нажатию кнопки не работает
2. спасибо, учту
3. у меня матрица 3 на 3, соответственно 2 цикла, но bx действительно изменяется на 4 (типа переход на следующую строку.. ) и кажется с 4-кой я ошиблась..

Сообщение отредактировано: 18192123 -
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #13


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


Программы целиком на ассемблере писал лет 10-15 назад, так что сейчас уже не вспомню, что какое прерывание делает.
Кроме того, непривычный синтаксис самого ассемблера. В свое время пользовался MASM.
У тебя программа начинатся с begin?
Как она знает, что начинать надо именно отсюда? Эо где-то прописывается?
Что делает первый цикл в 10 повторений? 10 раз подряд заполняет матрицу?
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #14


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Цитата(andriano @ 17.05.2008 21:07) *

У тебя программа начинатся с begin?
Как она знает, что начинать надо именно отсюда? Эо где-то прописывается?
Что делает первый цикл в 10 повторений? 10 раз подряд заполняет матрицу?

Да, выполнение программы начинается с begin. А узнаёт, т.к в самом конце прописываем end begin.
Да, 10 раз производится заполнение и вывод матрицы, потом вызывается макрокоманда задержки dely, далее курсор переводится в начало строки.
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #15


Гуру
*****

Группа: Пользователи
Сообщений: 1 168
Пол: Мужской
Реальное имя: Сергей Андрианов

Репутация: -  28  +


Ты располагаешь какими-либо средствами трассировки программы?
Если "да", попытайся выполнить пошагово, если "нет", то замени перевод курсора в начало строки его переводом на следующую строку. В общем, ошибку надо как-то локализовывать, а просмотр текста глазками - не самый эффективный путь.
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #16


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Цитата(andriano @ 17.05.2008 23:30) *

если "нет", то замени перевод курсора в начало строки его переводом на следующую строку.

так и сделала..курсор ни разу не попал на следующую строку..думаю, ошибка где-то в процедуре matr (даже до вывода сформированной матрицы)..
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #17


Профи
****

Группа: Пользователи
Сообщений: 920
Пол: Женский
Реальное имя: Марина

Репутация: -  2  +


Появился ещё один вариант генерации..но снова неудачный..Объясните мне пожалуста, как организовать генерацию чисел?!


dely    macro time; (1)
        local zd,c1,cikl,ii,ii1
        push cx
        push bx; (4)
        push bp; (5)
        push ax; (6)
        push dx; (7)
        mov cx,time
zd:     push cx; (9)
        mov bp,0;(10)
        mov bx,1;(11)
        
cikl:   
        inc BP;(12)
        mov ah,00h;(13)       
        int 1Ah;(14)
        cmp BP,1;(15)
        je ii
        jmp ii1
ii:     add bx,dx
ii1:                    ; (19)
        cmp bx,dx
        jne cikl
        pop cx
        loop zd;(23)
        pop cx;(24)
        pop bx;(25)
        pop bp;(26)
        pop ax;(27)
        pop dx;(28)
        endm;(29)

assume CS: code, DS: data
code segment
randomize proc
	mov ah,2Ch
	int 21h
	mov Rand1,ax
	mov Rand2,dx

randomize endp

random proc
	mov     ax,Rand1
  mov     bx,Rand2
  mov     cx,ax
  mul     RandA      ; RandA - любое число
  shl     cx,1
  shl     cx,1
  shl     cx,1
  add     ch,cl
  add     dx,cx
  add     dx,bx
  shl     bx,1
  shl     bx,1
  add     dx,bx
  add     dh,bl
  mov     cl,5
  shl     bx,cl
  add     dh,bl
  add     ax,1
  adc     dx,0
  mov     Rand1,ax
  mov     Rand2,dx
  mov     bx,sp                 
  mov     cx,dx                 
  mul     word ptr ss:[bx+4]    
  mov     ax,cx
  mov     cx,dx
  mul     word ptr ss:[bx+4]
  add     ax,cx
  adc     dx,0
  mov     ax,dx

random endp

matr proc
	mov cx,3
	mov si,0
	mov bx,0
	
	call randomize
	
external:
	push cx
	mov cx,3
	mov si,0
	
iternal:

	push cx
	push bx
rand:
	call random
	;call randomize
    cmp ax,30h ; число не менее
    jl rand
    cmp ax,39h ; число не более
    jg rand
	
	pop bx
	pop cx

    
	mov array[bx][si],ax
	add si,2
	loop iternal
	pop cx
	add bx,6
	loop external
	
	mov cx,3
	mov si,0
	mov bx,0
exshow:
	push cx
	mov cx,3
	mov si,0
ishow:
	mov ah,02h
	mov dx,array[bx][si]
	add dl,30h  
	int 21h
	add si,2
loop ishow
	lea dx,nl           ;переход на новую строку
	pop cx
	add bx,6
loop exshow
	ret
matr endp	

begin:

	mov AX, data
	mov DS, AX

miganie:
	push cx
	call matr
	dely 18
	mov ah,02h ;сдвижка курсора обратно в начало строки
	mov bh,00
	mov dh,15
	mov dl,0
	int 10h
	mov ah,06h
	mov dl,0ffh
	int 21h
	cmp al,44h
	jne miganie
	;mov AH,2Ch
	;int 21h
	;mov AH,02h
	; CH  - час,  CL - мин,  DH  - сек, DL - 1/100 сек
	;int 21h
exit:
	mov ax,4c00h
	int 21h
	
code ends

data segment
	array dw 3 dup(3 dup(0))
	i db 0
	nl db 13,10,'$'
	Rand1 dw 20
	Rand2 dw 10
	RandA dw 38
	;line db 15
data ends

stk segment stack
	dw 128
stk ends

end begin





Сообщение отредактировано: 18192123 -
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
сообщение
Сообщение #18


Гость






Urologia Priligy
 К началу страницы 
+ Ответить 

 Ответить  Открыть новую тему 
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0

 



- Текстовая версия 8.04.2025 16:31
500Gb HDD, 6Gb RAM, 2 Cores, 7 EUR в месяц — такие хостинги правда бывают
Связь с администрацией: bu_gen в домене octagram.name