Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

КМ МО-317 Шакиров А.Р. ЛР1

.docx
Скачиваний:
25
Добавлен:
28.06.2021
Размер:
135.8 Кб
Скачать

УФИМСКИЙ ГОСУДАРСТВЕННЫЙ АВИАЦИОННЫЙ ТЕХНИЧЕСКИЙ УНИВЕРСИТЕТ

ФАКУЛЬТЕТ ИНФОРМАТИКИ И РОБОТОТЕХНИКИ

КАФЕДРА ВЫЧИСЛИТЕЛЬНОЙ МАТЕМАТИКИ И КИБЕРНЕТИКИ

УТВЕРЖДАЮ

Проректор университета по научной работе

ФИО

"___" ______________ _______г.

Лабораторная работа № 1

«Генерирование случайных переменных»

по предмету: КОМПЬЮТЕРНОЕ МОДЕЛИРОВАНИЕ

Преподаватель

А. Ф. Валеева

Исполнитель

А. Р. Шакиров

Уфа - 2021

ЗАДАНИЕ

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

Ход работы

Реализуем получение равномерной случайной переменной на отрезке [a, b].

Входные данные:

a – минимальное значение (начало отрезка)

b – максимальное значение (конец отрезка)

Выходные данные:

result – значение равномерной случайной переменной на отрезке [a, b]

Алгоритм:

1. u = Uniform [0, 1]

2. result = a + (b - a) * u

Далее реализуем проверку принадлежности равномерной случайной переменной равномерному распределению.

Входные данные:

a – минимальное значение (начало отрезка)

b – максимальное значение (конец отрезка)

N – количество испытаний

Выходные данные:

критерий согласия – значение критерия согласия Пирсона

критерий согласия критический – критическое значение критерия согласия Пирсона при alpha = 0,05.

Алгоритм проверки:

  1. Создаем словарь испытаний, ключами которого являются целые числа от a до b, а значением является частота появления случайной переменной на интервале [ключ, ключ+1].

  2. счетчик испытаний = 0

  3. Пока количество испытаний меньше N:

    1. случайная переменная = равномерная случайная переменная на отрезке [a, b]

    2. ключ = целая часть от значения случайной переменной

    3. Если в словаре испытаний содержится получившийся ключ, то

      1. увеличиваем значение по данному ключу на 1.

    4. иначе

      1. по данному ключу заносим 1.

    5. Увеличиваем счетчик испытаний на 1

  1. сумма = 0

  2. Перебираем ключи словаря испытаний:

    1. частота появления значения в интервале = значение в словаре испытаний по данному ключу

    2. сумма += (ключ + 0,5) * частота появления значения в интервале

  3. выборочное среднее = сумма / N

  4. сумма = 0

  5. Перебираем ключи словаря испытаний

    1. частота появления значения в интервале = значение в словаре испытаний по данному ключу

    2. сумма += (ключ + 0,5) – выборочное среднее)2 * частота появления значения в интервале

  6. дисперсия = сумма / N

  7. среднеквадратичное отклонение = корень квадратный из дисперсии

  8. a* = выборочное среднее – ((корень квадратный от 3) * среднеквадратичное отклонение)

  9. b* = выборочное среднее + ((корень квадратный от 3) * среднеквадратичное отклонение)

  10. теоретическая плотность распределения = 1 / (b* - a*)

  11. число значений = количество ключей в словаре

  12. Создаем словарь теоретических испытаний, ключами которого являются целые числа от a до b, а значением является теоретическая частота появления случайной переменной на интервале [ключ, ключ+1].

  13. Заносим в словарь теоретических испытаний по ключу a значение = N * плотность * (a + 1 - a*).

  14. Если число значений > 2, то

    1. i = a + 1

    2. Пока i < b:

      1. Заносим в словарь теоретических испытаний по ключу i значение = N * теоретическая плотность распределения

  15. Заносим в словарь теоретических испытаний по ключу b значение = N * теоретическая плотность распределения * (b* – (b – 1)).

  16. критерий согласия = 0

  17. Перебираем ключи словаря испытаний

    1. частота появления в интервале = значение в словаре испытаний по данному ключу

    2. теоретическая частота появления в интервале = значение в словаре теоретических испытаний по данному ключу

    3. критерий согласия += (частота появления в интервале - теоретическая частота появления в интервале)2 / теоретическая частота

  18. критерий согласия критический = критическое значение критерия согласия Пирсона (хи квадрат) при alpha = 0,05 и степени свободы = число значений – 3

  19. Если критерий согласия < критерий согласия критический, то

    1. исследуемая случайная переменная принадлежит равномерному закону распределения

  20. иначе

    1. не принадлежит.

Далее реализуем получение Пуассоновской случайной переменной с интенсивностью lambda.

Входные данные:

lambda – среднее количество событий за фиксированный промежуток времени

Промежуточные данные:

p – вероятность того, что X=i

f – вероятность того, что X<=i

Выходные данные:

X – значение Пуассоновской случайной переменной

Алгоритм:

  1. u = Uniform [0, 1]

  2. p = число e в степени минус lambda

  3. f = p

  4. i = 0

  5. Пока не (u < f):

    1. p = lambda * p / (i + 1)

    2. f = f + p

    3. i = i + 1

  6. X = i

Далее реализуем проверку принадлежности Пуассоновской случайной переменной Пуассоновскому распределению.

Входные данные:

lambda – среднее количество событий за фиксированный промежуток времени

N – количество испытаний

Выходные данные:

критерий согласия – значение критерия согласия Пирсона

критерий согласия критический – критическое значение критерия согласия Пирсона при alpha = 0,05

Алгоритм проверки:

  1. Создаем словарь испытаний, ключами которого являются целые числа, а значением является частота появления случайной переменной.

  2. счетчик испытаний = 0

  3. Пока количество испытаний меньше N:

    1. случайная переменная = Пуассоновская случайная переменная при заданном lambda

    2. ключ = случайная переменная

    3. Если в словаре испытаний содержится получившийся ключ, то

      1. увеличиваем значение по данному ключу на 1.

    4. иначе

      1. по данному ключу заносим 1.

    5. Увеличиваем счетчик испытаний на 1

  1. сумма = 0

  2. Перебираем ключи словаря испытаний:

    1. частота появления значения случайной переменной = значение в словаре испытаний по данному ключу

    2. сумма += ключ * частота появления

  3. выборочное среднее = сумма / N

  4. число значений = количество ключей в словаре

  5. ожидаемое среднее = выборочное среднее

  6. Создаем словарь теоретических испытаний, ключами которого являются целые числа, а значением является частота появления случайной переменной.

  7. Перебираем ключи словаря испытаний:

    1. факториал = значение факториала от значения ключа

    2. вероятность = (число е в степени минус ожидаемое среднее) * (ожидаемое среднее в степени значения ключа) / факториал

    3. Заносим в словарь теоретических испытаний по текущему ключу значение = N * вероятность

  8. критерий согласия = 0

  9. Перебираем ключи словаря испытаний

    1. частота появления значения случайной переменной = значение в словаре испытаний по данному ключу

    2. теоретическая частота появления значения случайной переменной = значение в словаре теоретических испытаний по данному ключу

    3. критерий согласия += (частота появления значения случайной переменной - теоретическая частота появления значения случайной переменной)2 / теоретическая частота появления значения случайной переменной

  10. критерий согласия критический = критическое значение критерия согласия Пирсона (хи квадрат) при alpha = 0,05 и степени свободы = число значений – 2

  11. Если критерий согласия < критерий согласия критический, то

    1. исследуемая случайная переменная принадлежит равномерному закону распределения

  12. иначе

    1. не принадлежит.

результат работы программы

Проверка равномерного распределения случайной переменной:

Проверка Пуассоновского распределения случайной переменной:

ЛИСТИНГ ПРОГРАММЫ

// @ts-check

/**

* Критические значения хи квадрат

* при alpha = 0.05

* для числа степеней свободы от 1 до 20

*/

const chi2Criticals = [

3.8,

6,

7.8,

9.5,

11.1,

12.6,

14.1,

15.5,

16.9,

18.3,

19.7,

21,

22.4,

23.7,

25,

26.3,

27.6,

28.9,

30.1,

31.4

]

/**

* Получить значение согласно непрерывному равномерному распределению [min, max]

* @param {number} min

* @param {number} max

*/

function uniform(min, max) {

const u = Math.random()

return min + (max - min) * u

}

/**

* Получить значение согласно дискретному равномерному распределению [min, max]

* @param {number} lambda - параметр интенсивности

*/

function poisson(lambda) {

const u = Math.random()

let p = Math.exp(-lambda)

let f = p

let x = 0

while (!(u < f)) {

p = lambda * p / (x+1)

f += p

x += 1

}

return x

}

/**

* @typedef {Object} IResultItem

* @property {number} count - наблюдаемая частота

* @property {number?} theory - теоретическая частота

*/

/**

* Проверка непрерывного равномерного распределения

* @param {Record<number, IResultItem>} result - Результат выборки сгруппированный в единичные интервалы. 10 => интервал [10, 11)

* @param {number} N - объем выборки

*/

function checkUniform(result, N) {

const intervals = Object.keys(result).map((key) => +key)

const xCenters = intervals.map((begin) => +begin + 0.5) // т.к. интервал [i, i+1], то центр i + 0.5

// Выборочное среднее

const mean = 1 / N * intervals.reduce((acc, xi, index) => {

const ni = result[xi].count

return acc + (xCenters[index] * ni)

}, 0)

// Дисперсия

const variable = 1 / N * intervals.reduce((acc, xi, index) => {

const ni = result[xi].count

return acc + (ni * ((xCenters[index] - mean)**2))

}, 0)

// Среднеквадратичное отклонение

const sd = Math.sqrt(variable)

// оценки параметров a, b равномерного распределения

const a$ = mean - Math.sqrt(3) * sd

const b$ = mean + Math.sqrt(3) * sd

// плотность

const density = 1 / (b$ - a$)

// разбитие, число значений

const s = intervals.length

// теоритические частоты

result[intervals[0]].theory = N * density * (intervals[1] - a$)

if (s > 2) {

for (let i = 1; i < s-1; i++) {

result[intervals[i]].theory = N * density * 1 // 1 взят за ширину

}

}

result[intervals[s-1]].theory = N * density * (b$ - intervals[s-1])

// число степеней свободы k = s - 3

const k = s - 3

// критерий согласия Пирсона (хи квадрат)

const chi2 = intervals.reduce((acc, xi) => {

const ni = result[xi].count

const niTheory = result[xi].theory

return acc + ((ni - niTheory)**2 / niTheory)

}, 0)

const chi2Critical = chi2Criticals[k-1]

const resultTable = {}

Object.keys(result).forEach((key) => {

resultTable[`${key}-${+key+1}`] = result[key]

})

console.table(resultTable)

console.log(`Степень свободы k = ${k}`)

console.log(`Уровень значимости alpha = 0.05`)

console.log(`Хи квадрат наблюдаемое = ${chi2}`)

console.log(`Хи квадрат критическое = ${chi2Critical}`)

console.log(`Хи2 наблюдаемое ${chi2 < chi2Critical ? '<' : '>='} Хи2 критическое => исследуемая случайная переменная ${chi2 < chi2Critical ? '' : 'не '}принадлежит закону распределения`)

}

function factorial(n) {

if (n < 2) {

return 1

}

let result = 1

for (let i = 1; i <= n; i++) {

result *= i

}

return result

}

/**

* Проверка дискретного равномерного распределения

* @param {Record<number, IResultItem>} result - Результат выборки сгруппированный в единичные интервалы. 10 => интервал [10, 11)

* @param {number} N - объем выборки

*/

function checkPoisson(result, N) {

const values = Object.keys(result).map((str) => +str)

// разбитие, число значений

const s = values.length

// выборочное среднее

const mean = 1 / N * values.reduce((acc, xi) => {

const ni = result[xi].count

return acc + (+xi * ni)

}, 0)

const expectedLambda = mean

values.forEach((value) => {

const fact = factorial(value)

const pi = Math.exp(-expectedLambda) * (expectedLambda**value) / fact

result[value].theory = pi * N

})

// критерий согласия Пирсона (хи квадрат)

const chi2 = values.reduce((acc, xi) => {

const ni = result[xi].count

const niTheory = result[xi].theory

return acc + ((ni - niTheory)**2 / niTheory)

}, 0)

// степени свободы

const k = s - 2

// хи квадрат критическое при заданном k

const chi2Critical = chi2Criticals[k-1]

console.table(result)

console.log(`lamda теоретическая = ${expectedLambda}`)

console.log(`Степень свободы k = ${k}`)

console.log(`Уровень значимости alpha = 0.05`)

console.log(`Хи квадрат наблюдаемое = ${chi2}`)

console.log(`Хи квадрат критическое = ${chi2Critical}`)

console.log(`Хи2 наблюдаемое ${chi2 < chi2Critical ? '<' : '>='} Хи2 критическое => исследуемая случайная переменная ${chi2 < chi2Critical ? '' : 'не '}принадлежит закону распределения`)

}

/* Начало */

function main() {

const a = 1

const b = 5

const result1 = {}

for (let i = 0; i < (b-a); i++) {

result1[a+i] = { count: 0 }

}

const N1 = 200

console.log(`Равномерное непрерывное распределение (опытов ${N1}):`)

for (let index = 0; index < N1; index++) {

const x = Math.trunc(uniform(a,b))

result1[x].count += 1

}

// @ts-ignore

checkUniform(result1, N1)

console.log()

const result2 = {}

const N2 = 20000

const lambda = 5

console.log(`Пуассоновское распределение (lambda = ${lambda}, опытов ${N2}):`)

for (let index = 0; index < N2; index++) {

const x = poisson(lambda)

if (result2[x]) {

result2[x].count += 1

} else {

result2[x] = { count: 1 }

}

}

// @ts-ignore

checkPoisson(result2, N2)

}

main()

Вывод

В ходе лабораторной работы были получены навыки генерации случайных переменных. Также были получены навыки проверки по критерию согласия принадлежность исследуемой случайной переменной закону распределения.