реклама на сайте
подробности

 
 
2 страниц V   1 2 >  
Reply to this topicStart new topic
> Псевдослучайный генератор чисел, Нужен несложный алгоритм
Juras Pr.
сообщение Nov 22 2008, 18:05
Сообщение #1


Участник
*

Группа: Участник
Сообщений: 61
Регистрация: 26-04-08
Из: BY/MN
Пользователь №: 37 111



Подскажите несложный алгоритм, генерирующий значения от 0 до 31 по псевдослучайному закону. Сверхравномерность распределения значений мне не нужна, а нужно, чтобы было хоть подобие случайности. Работаю в основном на ассемблере.

Сообщение отредактировал Juras Pr. - Nov 22 2008, 18:06
Go to the top of the page
 
+Quote Post
777777
сообщение Nov 22 2008, 18:45
Сообщение #2


Профессионал
*****

Группа: Участник
Сообщений: 1 091
Регистрация: 25-07-07
Из: Саратов
Пользователь №: 29 357



Цитата(Juras Pr. @ Nov 22 2008, 21:05) *
Подскажите несложный алгоритм, генерирующий значения от 0 до 31 по псевдослучайному закону. Сверхравномерность распределения значений мне не нужна, а нужно, чтобы было хоть подобие случайности. Работаю в основном на ассемблере.

Например, сдвигаешь влево 32 бита, а вдвигаешь в 0-й исключающее или между 30-м и 27-м битом. Только в начале надо вдвинуть хотя бы одну единицу.

Пардон, не заметил что нужны числа до 31, а не 32 разряда. Тогда можно ограничиться одним байтом, а входные биты для искл. или подобрать экспериментально.

Сообщение отредактировал 777777 - Nov 22 2008, 18:47
Go to the top of the page
 
+Quote Post
Juras Pr.
сообщение Nov 22 2008, 18:54
Сообщение #3


Участник
*

Группа: Участник
Сообщений: 61
Регистрация: 26-04-08
Из: BY/MN
Пользователь №: 37 111



Спасибо, уже что-то есть. Идея понятна. А что если ещё использовать текущее значение какого-нибудь таймера? У меня в программе все 3 таймера заняты.
Go to the top of the page
 
+Quote Post
Tiny
сообщение Nov 22 2008, 19:08
Сообщение #4


Частый гость
**

Группа: Участник
Сообщений: 82
Регистрация: 10-07-06
Пользователь №: 18 720



Я делал так:
В таймере, который выполняет свою функцию помещаю
RAN = rand(); //Случайное во времени число
A1 = RAN%32; //Получаем случайное число от 0 до 32 (если не ошибаюсь насчет 32)
В нужный момент в программе использую число RAN, которое поучается врезултате модуляции результата функции rand() временным интервалом. А использоваться это значение будет в разные моменты времени с различным интервалом добавляя этим случайность.
Go to the top of the page
 
+Quote Post
777777
сообщение Nov 22 2008, 19:11
Сообщение #5


Профессионал
*****

Группа: Участник
Сообщений: 1 091
Регистрация: 25-07-07
Из: Саратов
Пользователь №: 29 357



Цитата(Juras Pr. @ Nov 22 2008, 21:54) *
Спасибо, уже что-то есть. Идея понятна. А что если ещё использовать текущее значение какого-нибудь таймера? У меня в программе все 3 таймера заняты.

Надо учесть, что таймеры работают от того же генератора, что и процессор. Поэтому результаты при кадждом запуске будут одинаковые. Если же сама программа будет их брать в "случайное" время (например при нажатии пользователем кнопки), то наверное можно. Но опять же, зависит от соотношения частоты таймера и частоты получения от него "случайного" числа: ведь значение таймера всегда увеличивается, поэтому если брать значение, скажем, 10 раз за оборот (переполнение), то значения будут не очень случайными, а монотонно возрастающими. А если один раз за 5-10 оборотов, то могут возникнуть "биения" между частотой таймера и частотой обращений и ты каждый раз будешь попадать примерно в одно и то же место, в результате получаемое значение будет медленно плыть. Так что таймером ИМХО лучше не пользоваться.
Go to the top of the page
 
+Quote Post
domowoj
сообщение Nov 22 2008, 19:13
Сообщение #6


Профессионал
*****

Группа: Участник
Сообщений: 1 548
Регистрация: 20-12-07
Из: г.Новосибирск
Пользователь №: 33 486



Можно сделать програмный сдвиговый регистр с обратными связями(ОС),
в зависимости от разрядности регистра - соответствующие ОС,

http://www.qrz.ru/schemes/contribute/secur...enerator1.shtml

Чем больше разрядность регистра, тем равномерней шум ГПСП.


--------------------
И на камнях растут деревья!
Go to the top of the page
 
+Quote Post
Juras Pr.
сообщение Nov 22 2008, 21:00
Сообщение #7


Участник
*

Группа: Участник
Сообщений: 61
Регистрация: 26-04-08
Из: BY/MN
Пользователь №: 37 111



Я попробовал сдвигать влево один байт, перед сдвигом беру 3-й и 6-й биты (с другими битами получается хуже), применяю к ним XOR и результат заношу после сдвига в 0-й бит байта. А в результат беру 5 младших битов. Перед запуском в этот регистр (байт) было занесено значение $55.
После прогона алгоритма 3 раза (по 32 каждый) получилась такая диграмма распределения.
Прикрепленное изображение

При увеличении числа прогонов диаграмма почти выравнивается.
Да, пользователь будет иногда нажимать кнопку, а таймер работает с высокой частотой, поэтому его я попробую задействовать. Этот алгоритм я буду писать на ассемблере.

Сообщение отредактировал Juras Pr. - Nov 22 2008, 21:03
Go to the top of the page
 
+Quote Post
Огурцов
сообщение Nov 23 2008, 00:20
Сообщение #8


Гуру
******

Группа: Участник
Сообщений: 3 928
Регистрация: 28-03-07
Из: РФ
Пользователь №: 26 588



Когда-то экспериментировал, только проверьте: длинну регистра нужно брать m = 2^n - 1, один бит крайний, второй может быть перед ним, либо самый первый, длиннна последовательности 2^m - 1, регистр инициализировать любым числом, отличным от нуля. Имхо, точно работает для 7, 15, 31 бит.

Сообщение отредактировал Огурцов - Nov 23 2008, 00:22
Go to the top of the page
 
+Quote Post
Juras Pr.
сообщение Nov 23 2008, 00:27
Сообщение #9


Участник
*

Группа: Участник
Сообщений: 61
Регистрация: 26-04-08
Из: BY/MN
Пользователь №: 37 111



Ближе всего мне 7-и битный вариант получается, буду на нём обкатывать, потом 5 бит попробую.
Да и по ссылке http://www.qrz.ru/...generator1.shtml для 7-и бит пример есть.
Важно, чтобы числа не повторялись 2 раза вподряд.
Go to the top of the page
 
+Quote Post
SKov
сообщение Nov 23 2008, 12:05
Сообщение #10


Знающий
****

Группа: Свой
Сообщений: 812
Регистрация: 22-01-05
Из: SPb
Пользователь №: 2 119



Цитата(Огурцов @ Nov 23 2008, 03:20) *
только проверьте: длинну регистра нужно брать m = 2^n - 1

Это, конечно, преувеличение.
Длину регистра можно брать любую. Для каждой длины m можно найти примитивный элемент поля GF(2^m), который даст на выходе регистра последовательность максимальной длины. В том числе можно подобрать и такой прим. элемент, который потребует только один сумматор в обратной связи. Кстати, этот вариант хоть и прост в реализации, но дает не очень хороший датчик. Чем больше сумматоров, тем датчик "псевдослучайнее".
Go to the top of the page
 
+Quote Post
Огурцов
сообщение Nov 23 2008, 13:22
Сообщение #11


Гуру
******

Группа: Участник
Сообщений: 3 928
Регистрация: 28-03-07
Из: РФ
Пользователь №: 26 588



Цитата(SKov @ Nov 23 2008, 12:05) *
Длину регистра можно брать любую.

Конечно, при условии, что есть возможность физически проверить всю последовательность.

Цитата(SKov @ Nov 23 2008, 12:05) *
В том числе можно подобрать и такой прим. элемент, который потребует только один сумматор в обратной связи.

Да, я на это и намекал.
Go to the top of the page
 
+Quote Post
ae_
сообщение Nov 23 2008, 13:30
Сообщение #12


Участник
***

Группа: Свой
Сообщений: 462
Регистрация: 2-04-07
Из: Иркутск
Пользователь №: 26 695



Цитата(Juras Pr. @ Nov 23 2008, 08:27) *
...
Важно, чтобы числа не повторялись 2 раза вподряд.

Можно сделать простой генератор ПСП по формуле x=(a*x+b)mod c
Вот пример для a=5, b=77, c=256
Код
.equ  rnd=R15
.equ  tmp=R16

mov  tmp, rnd
lsl  rnd
lsl  rnd
add  rnd, tmp
ldi  tmp, 77
add  rnd, tmp
mov  tmp, rnd


Так как нужно число до 32, то оставляем только 5 бит
Код
andi tmp, 0b00011111

Двух подряд одинаковых чисел точно не будет, но длина последовательности будет только 32. Начиная с 33 позиции серия будет повторятся.
Если взять старшие пять бит:
Код
lsr  tmp
lsr  tmp
lsr  tmp

То последовательность будет более случайная (длина серии 256), но будут встречаться подряд идущие одинаковые числа.
Go to the top of the page
 
+Quote Post
777777
сообщение Nov 23 2008, 13:43
Сообщение #13


Профессионал
*****

Группа: Участник
Сообщений: 1 091
Регистрация: 25-07-07
Из: Саратов
Пользователь №: 29 357



Цитата(ae_ @ Nov 23 2008, 16:30) *
Двух подряд одинаковых чисел точно не будет

Случайные - на значит разные! В случайной последовательности идущие подряд одинаковые числа не только могут, но и должны встречаться с вероятностью, вычисляемой теоретически.
Go to the top of the page
 
+Quote Post
Juras Pr.
сообщение Nov 23 2008, 13:43
Сообщение #14


Участник
*

Группа: Участник
Сообщений: 61
Регистрация: 26-04-08
Из: BY/MN
Пользователь №: 37 111



Цитата(ae_ @ Nov 23 2008, 15:30) *
Если взять старшие пять бит:
...
То последовательность будет более случайная (длина серии 256), но будут встречаться подряд идущие одинаковые числа.

Я сейчас так и сделал, только взял младшие 5 бит, а к результату применяю "исключающее или" текущего значения таймера, не заводя его значение в сам генератор. Результаты не повторяются, а до этого иногда было.
Go to the top of the page
 
+Quote Post
spf
сообщение Nov 23 2008, 16:05
Сообщение #15


Странник
****

Группа: Свой
Сообщений: 766
Регистрация: 29-08-05
Из: Екатеринбург
Пользователь №: 8 051



Посмотри, может что-то из этого поможет
http://vrtp.ru/index.php?showtopic=9500


--------------------
"Как много есть на свете вещей, которые мне не нужны!" Сократ
Go to the top of the page
 
+Quote Post

2 страниц V   1 2 >
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 18th July 2025 - 20:21
Рейтинг@Mail.ru


Страница сгенерированна за 0.01486 секунд с 7
ELECTRONIX ©2004-2016