diff --git a/powerlaw.py b/powerlaw.py index 20176aa..a8fff50 100644 --- a/powerlaw.py +++ b/powerlaw.py @@ -1163,7 +1163,7 @@ def sigma(self): return (self.alpha - 1) / sqrt(self.n) def _in_standard_parameter_range(self): - return self.alpha>1 + return self.alpha>0 def fit(self, data=None): if data is None and hasattr(self, 'parent_Fit'): @@ -1416,7 +1416,7 @@ def _initial_parameters(self, data): return (alpha, Lambda) def _in_standard_parameter_range(self): - return self.Lambda>0 and self.alpha>1 + return self.Lambda>0 and self.alpha>0 def _cdf_base_function(self, x): from mpmath import gammainc @@ -1928,13 +1928,13 @@ def cumulative_distribution_function(data, if all_unique: from numpy import arange - CDF = arange(n)/n + CDF = arange(1, n+1)/n else: #This clever bit is a way of using searchsorted to rapidly calculate the #CDF of data with repeated values comes from Adam Ginsburg's plfit code, #specifically https://github.com/keflavich/plfit/commit/453edc36e4eb35f35a34b6c792a6d8c7e848d3b5#plfit/plfit.py from numpy import searchsorted, unique - CDF = searchsorted(data, data,side='left')/n + CDF = searchsorted(data, data,side='right')/n unique_data, unique_indices = unique(data, return_index=True) data=unique_data CDF = CDF[unique_indices] diff --git a/testing/test_powerlaw.py b/testing/test_powerlaw.py index fce8385..7e29fb5 100644 --- a/testing/test_powerlaw.py +++ b/testing/test_powerlaw.py @@ -115,6 +115,39 @@ 'surnames': {} } +class BaseTestCase(unittest.TestCase): + """ + Test simple mathematical properties + """ + + def test_cumulative_distribution_function(self): + # Test all unique, and repeated values + X1 = [10, 30, 20, 20] + X2 = [10, 30, 20] + + for test_data in [X1, X2]: + X_sorted, CDF = powerlaw.cumulative_distribution_function(test_data) + # Check array is sorted + assert_allclose(X_sorted[-1], max(test_data)) + # CDF gives probability of less than or equal to some value. + # The last element is the max of the sample. All other elements + # are therefore smaller than or equal, and the CDF should be 1. + assert_allclose(CDF[-1], 1.0) + + def test_pdf(self): + import numpy as np + np.random.seed(0) + data = np.random.lognormal(mean=0, sigma=1, size=1000) + # We test limits + xmin = 0.1 + xmax = 0.2 + edges, hist = powerlaw.pdf(data, xmin=xmin, xmax=xmax) + area = np.sum(hist * np.diff(edges)) + # The area under a pdf should be 1 + assert_allclose(area, 1) + # Test limits + assert_allclose(edges[0], xmin) + assert_allclose(edges[-1], xmax) class FirstTestCase(unittest.TestCase):