QQplot для дискретного распределения - PullRequest
0 голосов
/ 18 января 2020

У меня есть набор, выборки которого представляют собой дискретные значения (в частности, размер очереди во времени). Теперь я хотел бы узнать, к какому распределению они принадлежат. Для достижения этой цели я бы поступил так же, как и для других величин, то есть построил график qqplot, запустив

import statsmodels.api as sm 
sm.qqplot(df, dist = 'geom', sparams = (.5,), line ='s', alpha = 0.3, marker ='.')

. Это работает, если dist не является дискретной случайной величиной (например, «exp»). или «норма»), и действительно, я использовал для получения некоторых результатов, но когда распределение является дискретным (скажем, «Geom»), я получаю

AttributeError: 'geom_gen' object has no attribute 'fit'

Я искал на Inte rnet, как сделать qqplot (или что-то подобное), чтобы определить, к какому распределению относятся мои образцы, но я ничего не нашел

Ответы [ 2 ]

0 голосов
/ 21 января 2020
def discreteQQ(x_sample):

    p_test = np.array([])
    for i in range(0, 1001):
        p_test = np.append(p_test, i/1000)
        i = i + 1

    x_sample = np.sort(x_sample)
    x_theor = stats.geom.rvs(.5, size=len(x_sample))
    ecdf_sample = np.arange(1, len(x_sample) + 1)/(len(x_sample)+1)

    x_theor = stats.geom.ppf(ecdf_sample, p=0.5)

    for p in p_test:
        plt.scatter(np.quantile(x_theor, p), np.quantile(x_sample, p), c = 'blue')

    plt.xlabel('Theoretical quantiles')
    plt.ylabel('Sample quantiles')
    plt.show()
0 голосов
/ 19 января 2020

Вы можете создать свой собственный график QQ, выполнив следующие действия: 1) Сортировать данные в порядке возрастания; 2) Создайте теоретическое распределение того же размера, что и ваши данные, и отсортируйте его. Другой подход заключается в преобразовании ecdf образца в квантили теоретического распределения с использованием обратной функции ecdf; 3) Постройте теоретическое распределение против себя - это даст вам прямую линию по диагонали; 4) Постройте данные выборки (ось Y) относительно теоретического распределения (ось X).

import numpy as np
from scipy import stats
import matplotlib.pyplot as plt

n = 100
p_theor = [1/2, 1/3, 1/4, 1/5] # The probabilities we check for
p_sample = 1/5 # The true probability of the sample distribution

# Generate the experimental data and sort it
x_sample = np.sort(stats.geom.rvs(p_sample, size=n))

# EDCF calculation
ecdf_sample = np.arange(1, len(x_sample) + 1)/(len(x_sample)+1)

# Generate Q-Q plot for the different hypothetical distributions
n = x_sample.shape[0]
plt.subplots(2, 2)
for i, p in enumerate(p_theor):
    # Generate the theoretical distribution and sort it
    # x_hyp = np.sort(stats.geom.rvs(p, size=n))
    # Or inverse the samle ecdf as done in the following line
    x_theor = stats.geom.ppf(ecdf_sample, p=p)
    plt.subplot(2, 2, i+1)
    plt.scatter(x_theor, x_theor, label='p_theor = {}'.format(np.round(p, 2)))
    plt.scatter(x_theor, x_sample, label='p_sample = 0.2')
    plt.xlabel('Theoretical quantiles')
    plt.ylabel('Sample quantiles')
    plt.legend()

enter image description here

Редактировать: вот функция, которая выводит график QQ для распределения геометрии c. По умолчанию теоретическое распределение рассчитывается с p = 0,5. Вы можете изменить его, указав альтернативную вероятность в качестве второго параметра функции geom_QQ_plot. Помните, что график QQ должен иметь две кривые: теоретическая и теоретическая выборка, чтобы понять, соответствуют ли выборка и теоретические распределения. Ниже образец был сгенерирован с использованием p = 0.2, тогда как теоретические квантили были сгенерированы с использованием p = 0.5. Расхождение между выборкой и гипотетическим распределением очевидно.

def geom_QQ_plot(x_sample, p=0.5):
    """ Plot the Q-Q plot of the geometric distribution """
    ecdf_sample = np.arange(1, len(x_sample) + 1)/(len(x_sample)+1)
    x_theor = stats.geom.ppf(ecdf_sample, p=p)
    plt.scatter(x_theor, x_theor, label='theor-theor quantiles')
    plt.scatter(x_theor, x_sample, label='theor-sample quantiles')
    plt.xlabel('Theoretical quantiles')
    plt.ylabel('Sample quantiles')
    plt.legend()

geom_QQ_plot(x_sample)

enter image description here

...