HiveBrain v1.2.0
Get Started
← Back to all entries
patternpythonModerate

Calculating population standard deviation

Submitted by: @import:stackexchange-codereview··
0
Viewed 0 times
calculatingstandarddeviationpopulation

Problem

This is a script I have written to calculate the population standard deviation. I feel that this can be simplified and also be made more pythonic.

from math import sqrt

def mean(lst):
    """calculates mean"""
    sum = 0
    for i in range(len(lst)):
        sum += lst[i]
    return (sum / len(lst))

def stddev(lst):
    """calculates standard deviation"""
    sum = 0
    mn = mean(lst)
    for i in range(len(lst)):
        sum += pow((lst[i]-mn),2)
    return sqrt(sum/len(lst)-1)

numbers = [120,112,131,211,312,90]

print stddev(numbers)

Solution

The easiest way to make mean() more pythonic is to use the sum() built-in function.

def mean(lst):
    return sum(lst) / len(lst)


Concerning your loops on lists, you don't need to use range(). This is enough:

for e in lst:
   sum += e


Other comments:

  • You don't need parentheses around the return value (check out PEP 8 when you have a doubt about this).



  • Your docstrings are useless: it's obvious from the name that it calculates the mean. At least make them more informative ("returns the mean of lst").



  • Why do you use "-1" in the return for stddev? Is that a bug?



  • You are computing the standard deviation using the variance: call that "variance", not sum!



  • You should type pow(e-mn,2), not pow((e-mn),2). Using parentheses inside a function call could make the reader think he's reading a tuple (eg. pow((e,mn),2) is valid syntax)



  • You shouldn't use pow() anyway, ** is enough.



This would give:

def stddev(lst):
    """returns the standard deviation of lst"""
    variance = 0
    mn = mean(lst)
    for e in lst:
        variance += (e-mn)**2
    variance /= len(lst)

    return sqrt(variance)


It's still way too verbose! Since we're handling lists, why not using list comprehensions?

def stddev(lst):
    """returns the standard deviation of lst"""
    mn = mean(lst)
    variance = sum([(e-mn)**2 for e in lst]) / len(lst)
    return sqrt(variance)


This is not perfect. You could add tests using doctest. Obviously, you should not code those functions yourself, except in a small project. Consider using Numpy for a bigger project.

Code Snippets

def mean(lst):
    return sum(lst) / len(lst)
for e in lst:
   sum += e
def stddev(lst):
    """returns the standard deviation of lst"""
    variance = 0
    mn = mean(lst)
    for e in lst:
        variance += (e-mn)**2
    variance /= len(lst)

    return sqrt(variance)
def stddev(lst):
    """returns the standard deviation of lst"""
    mn = mean(lst)
    variance = sum([(e-mn)**2 for e in lst]) / len(lst)
    return sqrt(variance)

Context

StackExchange Code Review Q#9222, answer score: 14

Revisions (0)

No revisions yet.