Mam listę, dla której lubię obliczać wariancję próbki . Kiedy używam numpy.var, otrzymuję inny wynik z funkcji, którą zdefiniowałem.

Czy ktoś może mi pomóc zrozumieć, czego mi brakuje?

my_ls = [227, 222, 218, 217, 225, 218, 216, 229, 228, 221]


def calc_mean(ls):

        sum_tmp = 0
        for i in ls:
                sum_tmp = sum_tmp + i

        return round(sum_tmp/len(ls), 2)

def calc_var(ls):

        tmp_mean = calc_mean(ls)

        tmp_sum = 0
        for i in ls:
                tmp_sum = tmp_sum + ((i - tmp_mean)**2)

        return round(tmp_sum/(len(ls)-1), 2)


calc_var(my_ls)
>>> 23.66

np.var(my_ls)
>>> 21.29

23,66 to moja pożądana wartość.

2
loki 3 kwiecień 2020, 13:10

4 odpowiedzi

Najlepsza odpowiedź

Mianownikiem w przypadku np.var(my_ls) jest domyślnie całkowita wielkość próby (N).

Możesz użyć Delta Degrees of Freedom (ddof) w numpy, aby pokazać, że obliczasz wariancję próbki przez ustawienie ddof = 1 dla średniego stopnia swobody. To znaczy. twoim mianownikiem jest teraz (N-1)

np.var(my_ls,ddof=1)
>>> 23.66
3
compuphys 3 kwiecień 2020, 10:27

Używasz nieobciążonego wzoru na wariancję, tj. Dzielisz sumowanie przez N-1, podczas gdy np.var wydaje się obliczać normalizację wariancji przez całkowitą liczbę elementów w wektorze.

Sprawdź na przykład tutaj, sekcja „Przykładowe wariancje”.

1
Eddymage 3 kwiecień 2020, 10:19

Możesz użyć parametru ddof np.var(), co oznacza „stopnie swobody”:

np.var(my_ls, ddof=1)
# 23.65555555555555

Aby doprowadzić Cię do pożądanego rezultatu.

Zasadniczo dzielisz sumę kwadratów przez n - 1, a np.var() dzieli się przez n - ddof, co domyślnie wynosi 0. Dyskusję na te tematy można znaleźć w Wikipedii.

2
norok2 8 kwiecień 2020, 10:44

Twoja funkcja calc_var(ls) nie implementuje wariancji formuła:

Wariancja jest średnią kwadratów odchyleń od średniej, tj. var = mean(abs(x - x.mean())**2).

Możesz użyć:

def calc_var(ls):

        tmp_mean = calc_mean(ls)

        means = []
        for i in ls:
                means.append((i - tmp_mean)**2)

        var = calc_mean(means)
        return round(var, 2)

print(calc_var(my_ls))
print(np.var(my_ls))

Wynik:

21.29
21.29
1
kederrac 3 kwiecień 2020, 15:13