Оригинальный DVD-ROM: eXeL@B DVD !
eXeL@B ВИДЕОКУРС !

ВИДЕОКУРС ВЗЛОМ
выпущен 2 июня!


УЗНАТЬ БОЛЬШЕ >>
Домой | Статьи | RAR-cтатьи | FAQ | Форум | Скачать | Видеокурс
Новичку | Ссылки | Программирование | Интервью | Архив | Связь

ПРОГРАММИРОВАНИЕ НА C и С++



Программисты долго мучаются с кодом прогаммы, изучают С++, WinAPI функции, MSDN. Потом пишут банальную систему защиты или навешивают банальный протектор, а крэкеры и реверсеры справляются с такой защитой за 5 минут. В итоге, продажи программы почти нулевые. Чтобы такого не допустить, тут самому надо немного поднабрать опыта отладки, реверсинга, тот же отладчик Ollydbg изучить или дизассемблер IDA Pro. Но где искать по крохам эти знания? Нет, конечно можно годами "методом тыка" разбираться, но куда быстрее видеокурс специальный посмотреть. Вот тут он есть: ссылка. Автор курса с большим опытом и объясняет понятно, я из этого курса много узнал про то как работает компьютер, процессор, про инструменты специальные и как с ними работать. Мои коллеги программисты на работе ничего такого и не знают, теперь я им нос утру.

Примитивные и грязные генераторы случайных чисел


Генераторы случайных чисел, поставляемые системой

В стандарте ANSI-C имеется функция rand(), выдающая равномерно распределенное число от 0 до RAND_MAX, и связанная с ней функция srand(), производящая начальную установку счетчика. Описание в файле <stdlib.h>. Почти все подобные генераторы используют рекуррентную последовательность
I(n+1)=(a*I(n)+c)(mod m).
Число a называется мультипликатором, число c инкрементом, а число m - модулем.

Такой выбор может послужить серьезным ограничением на статистические свойства последовательности случайных чисел. Кроме того, в большинстве случаев RAND_MAX=35767, что значительно меньше, чем диапазон изменения целых чисел. В некоторых испытаниях теория рекомендует 106 - 109 случайных проб, но, пользуясь подобным счетчиком, можно получить не более RAND_MAX одинаковых случайных чисел, т.е. в 30 тыс.- 30 млн. раз меньше рекомендуемого.

Генератор ANSI-C был опубликован комиссией как "пример". Мы его тоже приводим, но как "не рекомендованный" для серьезных приложений.


 
 /* (в модуле stdlib.h) */
 
 #define RAND_MAX 32767
 
 
 
 /* "пример" от комитета ANSI-C */
 
 unsigned long next=1;
 
 
 
 int rand(void) {
 
  next=next*1103515245+12345;
 
  return((unsigned int)(next/65536)%32768);
 
 }
 
 
 
 void srand(unsigned int seed) {
 
  next=seed;
 
 }
 
 

Мультипликатор и инкремент этого примера (который, скорее всего и поставляется со стандартной библиотекой C) не являются оптимальными. Об оптимальных константах для такого рода последовательностей ниже.


Быстрые и грязные генераторы случайных чисел, отличные от "стандарта"

Иногда требуется произвести не слишком изысканную последовательных случайных действительных или целых чисел, при этом код генерации случайного числа желательно держать "в строке" (для скорости) либо производить выбор для различного возможного числа значащих битов беззнакового целого числа. Ниже приводятся фрагменты программ, осуществляющие подобную генерацию для нормального распределения действительных чисел между 0 и 1 и для целых чисел произвольного диапазона.

 
 Генерация случайного действительного числа, равномерно распределенного
 
 от 0 до 1 и целого, равномерно распределенного от jlow до jhigh.
 
 
 
 
 
 static unsigned long iran;
 
 unsigned long rand_a,rand_c,rand_m;
 
 float fran;
 
 int jran;
 
 ...................
 
 /* floating-point fran uniformly from 0 to 1 */
 
 iran=(iran*rand_a+rand_c)%rand_m;
 
 fran=(float)iran/(float)rand_m;
 
 ..................
 
 /* integer jran between jlow and jhigh */
 
 iran=(iran*rand_a+rand_c)%rand_m;
 
 jran=jlow+((jhigh-jlow+1)*iran)/im;
 
 

Ниже приводятся оптимальные значения коэффициентов rand_a, rand_c, rand_m для различного значения числа значащих бит в беззнаковом целом.

bitsrand_mrand_arand_c
2060751061283
2178752111663
2278754211663
23 607513661283
66359361399
119794302531
24 144069673041
292824196173
5312517111213
25 1296017412731
1400015412957
2187012914621
311046256571
13996820529573
26 2928212556173
8100042117117
13445628128411
27 86436109318257
121500102125673
25920042154773
28 117128127724749
121500204125673
31250074166037
29 145800366130809
175000266136979
233280186149297
244944159751749
30 139968387729573
214326361345289
7140251366150889
31 134456812128411
259200714154773
32 233280930149297
7140254096150889

Самый быстрый генератор для 32-битового представления целых и действительных чисел.

В большинстве случаев, число типа unsigned long имеет 32 бита. В этом случае для генерации числа в диапазоне 0 - 232-1 достаточно простого умножения на мультипликатор и сложения с инкрементом. Деление по модулю будет произведено автоматически при переполнении. Значения мультипликатора и инкремента для этого случая получены в исследованиях D. Knuth и H.W. Lewis.


 
 /* генерация целого числа от 0 до 0xFFFFFFFF. */
 
 static unsigned long iran;
 
 ...........
 
 iran=1664525L*iran+1013904223L;
 
 

Для реализации на этой основе очень быстрого генератора равномерного распределения действительных чисел от 0 до 1 важно, что floating-point single precision numbers (тип float) в большинстве случаев представлены также 32 битами. Кроме того, во многих случаях (включая SUN, ALPHA, Silicon Graphics и IBM PC) представление этого числа отвечает одному стандарту IEEE. Для машины VAX это не так. Грязным трюком, позволяющим избегнуть деления на действительное число, является маскировка экспоненты и дальнейшее вычитание из числа единицы. Необходимые коэффициенты в программе приведены для IEEE (по умолчанию) и для VAX.


 
 static unsigned long iran;
 
 unsigned long temp;
 
 float fran;
 
 ..........
 
 #if !defined(VAX)
 
  static unsigned long jflone=0x3f800000;
 
  static unsigned long jflmsk=0x007fffff;
 
 #else
 
  static unsigned long jflone=0x00004080;
 
  static unsigned long jflmsk=0xffff007f;
 
 #endif
 
 ..........
 
 iran=1664525L*iran+1013904223L;
 
 temp=jflone|(jflmsk&iran);
 
 fran=(*(float *)&temp)-1.F;
 
 

С точки зрения программиста, занимающегося численными методами, а не железом, этот генератор является "особо грязным", поскольку реализация зависит от представления чисел в компьютере. Впрочем, этот генератор в подавляющем большинстве практических случаев работает верно, а главное - очень быстро.



<< ВЕРНУТЬСЯ В ПОДРАЗДЕЛ

<< ВЕРНУТЬСЯ В ОГЛАВЛЕНИЕ




Материалы находятся на сайте https://exelab.ru/pro/



Оригинальный DVD-ROM: eXeL@B DVD !


Вы находитесь на EXELAB.rU
Проект ReactOS