Есть задача по случайной генерации ряда(массива), состоящего из всех чисел заданного диапазона, но без повторов. Вот как решаю сейчас. Код (Text): randomize; FOR i:=0 to NN-1 do a_flag[i]:=True; //инициализация массива флажков FOR i:=0 to NN-1 do begin tmp:=random(NN); // j:=i; WHILE True do begin if a_flag[tmp]then begin // если место "не занято" a_goal[j]:=tmp; // то вставляем случайное число a_flag[tmp]:=False; // и "занимаем место" break; end; tmp:=tmp+1; // если место "занято", то переходим к cледующему //??? а насколько вот это решение "уничтожает" случайность ???? if tmp=NN then tmp:=0; // если при переходе доходим до границы до уходим в начало диапазона. end; end; На выходе получаем a_goal какой нам надо. Но надо это получать раз в 5 быстрее. А лучше в 10 Есть более быстрый алгоритм? Спасибо большое.
или так Код (Text): //LastNum - максимальное число из диапазона //FirstNum - мин-ое число из диапазона int Array1[n]; int Array2[n]; int x = LastNum - FirstNum; int tmp; for (int i = 0; i < n; i++) { Array1[i] = FirstNum + i; } for (int i = 0; i < n; i++) { if (!x) x = 1; tmp = Random()%x; Array2[i] = Array1[tmp]; Array1[tmp] = Array1[x]; x--; } Правда последние оставшиеся 2 числа извлекуться в заранее известном порядке
Д. Кнут. "Искусство программирования". Том 2. Алгоритм 3.4.2P. Для перестановки элементов {0,...,NN-1} на паскале это выглядит примерно так: Код (Text): randomize; for i:=0 to NN-1 do begin tmp:=Random(i+1); a_goal[i]:=a_goal[tmp]; a_goal[tmp]:=i; end; В предположении равновероятности и независимости результатов Random все возможные перестановки получаются с одной и той же вероятностью (равной, как нетрудно догадаться, 1/NN!).
А насколько случаен должен быть ряд вообще? Если достаточно просто нормального распределения, то достаточно следующего алгоритма: Ni=((N(i-1)*X+Y) xor Z) mod NN X - взаимно простое с NN, Y,Z - любое подобрать числа для хорошего распределения можно эксперементальным путем в зависимости от NN.
Большое спасибо всем. Сначала у меня некоторое сомнение вызвал вариант предложенный diamond, но потом понял, что он мне подходит... Единственный вопрос, есть реализация гсч для дельфи быстрее чем стандартный дельфийский random?
можешь попробовать формулу x := a * x + b b = 2 * m + 1 a = 4 * n + 1 m и n - какие-нить целые числа.
В частности, если a=5 и b=1, то получается такой быстрый код lea eax,[eax+eax*4] inc eax должно по теории пробегать все 2^32 значений, включая ноль.
persicum Это T-function. Это ни под каким микроскопом не случайно и даже не псевдослучайно. И это вообще не по теме. /me может только вздыхать... HN2008 Держись как можно дальше от таких "генераторов". А перемешивать легко, как это в RC4 сделано – asd правильно написал. Надо только random быстрый...