pvlib 0.10.4__py3-none-any.whl → 0.10.5__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
pvlib/bifacial/utils.py CHANGED
@@ -4,6 +4,7 @@ modeling.
4
4
  """
5
5
  import numpy as np
6
6
  from pvlib.tools import sind, cosd, tand
7
+ from scipy.integrate import trapezoid
7
8
 
8
9
 
9
10
  def _solar_projection_tangent(solar_zenith, solar_azimuth, surface_azimuth):
@@ -220,7 +221,7 @@ def vf_ground_sky_2d_integ(surface_tilt, gcr, height, pitch, max_rows=10,
220
221
  vf = vf_ground_sky_2d(r, gcr, z, pitch, height, max_rows)
221
222
  fz_sky[:, k] = vf[:, 0] # remove spurious rotation dimension
222
223
  # calculate the integrated view factor for all of the ground between rows
223
- return np.trapz(fz_sky, z, axis=0)
224
+ return trapezoid(fz_sky, z, axis=0)
224
225
 
225
226
 
226
227
  def _vf_poly(surface_tilt, gcr, x, delta):
pvlib/iotools/srml.py CHANGED
@@ -92,7 +92,7 @@ def read_srml(filename, map_variables=True):
92
92
  # Mask data marked with quality flag 99 (bad or missing data)
93
93
  for col in columns[::2]:
94
94
  missing = data[col + '_flag'] == 99
95
- data[col] = data[col].where(~(missing), np.NaN)
95
+ data[col] = data[col].where(~(missing), np.nan)
96
96
  return data
97
97
 
98
98
 
@@ -175,7 +175,8 @@ def _format_index(df):
175
175
  @deprecated('0.10.0', alternative='pvlib.iotools.get_srml', removal='0.11.0')
176
176
  def read_srml_month_from_solardat(station, year, month, filetype='PO',
177
177
  map_variables=True):
178
- """Request a month of SRML data and read it into a Dataframe.
178
+ """
179
+ Request a month of SRML data and read it into a Dataframe.
179
180
 
180
181
  The SRML is described in [1]_.
181
182
 
pvlib/iotools/surfrad.py CHANGED
@@ -152,7 +152,7 @@ def read_surfrad(filename, map_variables=True):
152
152
 
153
153
  data = _format_index(data)
154
154
  missing = data == -9999.9
155
- data = data.where(~missing, np.NaN)
155
+ data = data.where(~missing, np.nan)
156
156
 
157
157
  if map_variables:
158
158
  data.rename(columns=VARIABLE_MAP, inplace=True)
pvlib/location.py CHANGED
@@ -439,8 +439,10 @@ def lookup_altitude(latitude, longitude):
439
439
  # 255 is a special value that means nodata. Fallback to 0 if nodata.
440
440
  if alt == 255:
441
441
  return 0
442
+ # convert from np.uint8 to float so that the following operations succeed
443
+ alt = float(alt)
442
444
  # Altitude is encoded in 28 meter steps from -450 meters to 6561 meters
443
445
  # There are 0-254 possible altitudes, with 255 reserved for nodata.
444
446
  alt *= 28
445
447
  alt -= 450
446
- return float(alt)
448
+ return alt
pvlib/pvarray.py CHANGED
@@ -311,11 +311,13 @@ def huld(effective_irradiance, temp_mod, pdc0, k=None, cell_type=None):
311
311
 
312
312
  :py:func:`huld` is a component of the PV performance model implemented in
313
313
  PVGIS. Among other components, the full PVGIS model includes:
314
- - the Faiman model for module temperature
315
- :py:func:`pvlib.temperature.faiman`
316
- - the Martin and Ruiz model for the incidence angle modifier (IAM)
317
- :py:func:`pvlib.iam.martin_ruiz`
318
- - a custom model for a spectral adjustment factor
314
+
315
+ - the Faiman model for module temperature
316
+ :py:func:`pvlib.temperature.faiman`
317
+ - the Martin and Ruiz model for the incidence angle modifier (IAM)
318
+ :py:func:`pvlib.iam.martin_ruiz`
319
+ - a custom model for a spectral adjustment factor
320
+
319
321
  The PVGIS API (see :py:func:`pvlib.iotools.get_pvgis_hourly`) returns
320
322
  broadband plane-of-array irradiance (``poa_global``) and DC power (``P``).
321
323
  ``poa_global`` is irradiance before applying the IAM and spectral
pvlib/pvsystem.py CHANGED
@@ -7,7 +7,7 @@ from collections import OrderedDict
7
7
  import functools
8
8
  import io
9
9
  import itertools
10
- import os
10
+ from pathlib import Path
11
11
  import inspect
12
12
  from urllib.request import urlopen
13
13
  import numpy as np
@@ -1487,8 +1487,10 @@ def calcparams_desoto(effective_irradiance, temp_cell,
1487
1487
  '''
1488
1488
  Calculates five parameter values for the single diode equation at
1489
1489
  effective irradiance and cell temperature using the De Soto et al.
1490
- model described in [1]_. The five values returned by calcparams_desoto
1491
- can be used by singlediode to calculate an IV curve.
1490
+ model. The five values returned by ``calcparams_desoto`` can be used by
1491
+ singlediode to calculate an IV curve.
1492
+
1493
+ The model is described in [1]_.
1492
1494
 
1493
1495
  Parameters
1494
1496
  ----------
@@ -1958,9 +1960,9 @@ def calcparams_pvsyst(effective_irradiance, temp_cell,
1958
1960
 
1959
1961
 
1960
1962
  def retrieve_sam(name=None, path=None):
1961
- '''
1962
- Retrieve latest module and inverter info from a local file or the
1963
- SAM website.
1963
+ """
1964
+ Retrieve latest module and inverter info from a file bundled with pvlib,
1965
+ a path or an URL (like SAM's website).
1964
1966
 
1965
1967
  This function will retrieve either:
1966
1968
 
@@ -1971,10 +1973,14 @@ def retrieve_sam(name=None, path=None):
1971
1973
 
1972
1974
  and return it as a pandas DataFrame.
1973
1975
 
1976
+ .. note::
1977
+ Only provide one of ``name`` or ``path``.
1978
+
1974
1979
  Parameters
1975
1980
  ----------
1976
1981
  name : string, optional
1977
- Name can be one of:
1982
+ Use one of the following strings to retrieve a database bundled with
1983
+ pvlib:
1978
1984
 
1979
1985
  * 'CECMod' - returns the CEC module database
1980
1986
  * 'CECInverter' - returns the CEC Inverter database
@@ -1985,7 +1991,7 @@ def retrieve_sam(name=None, path=None):
1985
1991
  * 'ADRInverter' - returns the ADR Inverter database
1986
1992
 
1987
1993
  path : string, optional
1988
- Path to the SAM file. May also be a URL.
1994
+ Path to a CSV file or a URL.
1989
1995
 
1990
1996
  Returns
1991
1997
  -------
@@ -1997,7 +2003,11 @@ def retrieve_sam(name=None, path=None):
1997
2003
  Raises
1998
2004
  ------
1999
2005
  ValueError
2000
- If no name or path is provided.
2006
+ If no ``name`` or ``path`` is provided.
2007
+ ValueError
2008
+ If both ``name`` and ``path`` are provided.
2009
+ KeyError
2010
+ If the provided ``name`` is not a valid database name.
2001
2011
 
2002
2012
  Notes
2003
2013
  -----
@@ -2030,38 +2040,38 @@ def retrieve_sam(name=None, path=None):
2030
2040
  CEC_Date NaN
2031
2041
  CEC_Type Utility Interactive
2032
2042
  Name: AE_Solar_Energy__AE6_0__277V_, dtype: object
2033
- '''
2034
-
2035
- if name is not None:
2036
- name = name.lower()
2037
- data_path = os.path.join(
2038
- os.path.dirname(os.path.abspath(__file__)), 'data')
2039
- if name == 'cecmod':
2040
- csvdata = os.path.join(
2041
- data_path, 'sam-library-cec-modules-2019-03-05.csv')
2042
- elif name == 'sandiamod':
2043
- csvdata = os.path.join(
2044
- data_path, 'sam-library-sandia-modules-2015-6-30.csv')
2045
- elif name == 'adrinverter':
2046
- csvdata = os.path.join(
2047
- data_path, 'adr-library-cec-inverters-2019-03-05.csv')
2048
- elif name in ['cecinverter', 'sandiainverter']:
2049
- # Allowing either, to provide for old code,
2050
- # while aligning with current expectations
2051
- csvdata = os.path.join(
2052
- data_path, 'sam-library-cec-inverters-2019-03-05.csv')
2053
- else:
2054
- raise ValueError(f'invalid name {name}')
2055
- elif path is not None:
2056
- if path.startswith('http'):
2057
- response = urlopen(path)
2058
- csvdata = io.StringIO(response.read().decode(errors='ignore'))
2059
- else:
2060
- csvdata = path
2043
+ """
2044
+ # error: path was previously silently ignored if name was given GH#2018
2045
+ if name is not None and path is not None:
2046
+ raise ValueError("Please provide either 'name' or 'path', not both.")
2061
2047
  elif name is None and path is None:
2062
- raise ValueError("A name or path must be provided!")
2063
-
2064
- return _parse_raw_sam_df(csvdata)
2048
+ raise ValueError("Please provide either 'name' or 'path'.")
2049
+ elif name is not None:
2050
+ internal_dbs = {
2051
+ "cecmod": "sam-library-cec-modules-2019-03-05.csv",
2052
+ "sandiamod": "sam-library-sandia-modules-2015-6-30.csv",
2053
+ "adrinverter": "adr-library-cec-inverters-2019-03-05.csv",
2054
+ # Both 'cecinverter' and 'sandiainverter', point to same database
2055
+ # to provide for old code, while aligning with current expectations
2056
+ "cecinverter": "sam-library-cec-inverters-2019-03-05.csv",
2057
+ "sandiainverter": "sam-library-cec-inverters-2019-03-05.csv",
2058
+ }
2059
+ try:
2060
+ csvdata_path = Path(__file__).parent.joinpath(
2061
+ "data", internal_dbs[name.lower()]
2062
+ )
2063
+ except KeyError:
2064
+ raise KeyError(
2065
+ f"Invalid name {name}. "
2066
+ + f"Provide one of {list(internal_dbs.keys())}."
2067
+ ) from None
2068
+ else: # path is not None
2069
+ if path.lower().startswith("http"): # URL check is not case-sensitive
2070
+ response = urlopen(path) # URL is case-sensitive
2071
+ csvdata_path = io.StringIO(response.read().decode(errors="ignore"))
2072
+ else:
2073
+ csvdata_path = path
2074
+ return _parse_raw_sam_df(csvdata_path)
2065
2075
 
2066
2076
 
2067
2077
  def _normalize_sam_product_names(names):
@@ -2254,10 +2264,9 @@ def sapm(effective_irradiance, temp_cell, module):
2254
2264
  module['IXO'] * (module['C4']*Ee + module['C5']*(Ee**2)) *
2255
2265
  (1 + module['Aisc']*(temp_cell - temp_ref)))
2256
2266
 
2257
- # the Ixx calculation in King 2004 has a typo (mixes up Aisc and Aimp)
2258
2267
  out['i_xx'] = (
2259
2268
  module['IXXO'] * (module['C6']*Ee + module['C7']*(Ee**2)) *
2260
- (1 + module['Aisc']*(temp_cell - temp_ref)))
2269
+ (1 + module['Aimp']*(temp_cell - temp_ref)))
2261
2270
 
2262
2271
  if isinstance(out['i_sc'], pd.Series):
2263
2272
  out = pd.DataFrame(out)
@@ -2536,7 +2545,7 @@ def singlediode(photocurrent, saturation_current, resistance_series,
2536
2545
 
2537
2546
 
2538
2547
  def max_power_point(photocurrent, saturation_current, resistance_series,
2539
- resistance_shunt, nNsVth, d2mutau=0, NsVbi=np.Inf,
2548
+ resistance_shunt, nNsVth, d2mutau=0, NsVbi=np.inf,
2540
2549
  method='brentq'):
2541
2550
  """
2542
2551
  Given the single diode equation coefficients, calculates the maximum power
pvlib/scaling.py CHANGED
@@ -13,8 +13,10 @@ from scipy.spatial.distance import pdist
13
13
  def wvm(clearsky_index, positions, cloud_speed, dt=None):
14
14
  """
15
15
  Compute spatial aggregation time series smoothing on clear sky index based
16
- on the Wavelet Variability model of Lave et al. [1]_, [2]_. Implementation
17
- is basically a port of the Matlab version of the code [3]_.
16
+ on the Wavelet Variability model.
17
+
18
+ This model is described in Lave et al. [1]_, [2]_.
19
+ Implementation is basically a port of the Matlab version of the code [3]_.
18
20
 
19
21
  Parameters
20
22
  ----------
pvlib/singlediode.py CHANGED
@@ -58,7 +58,7 @@ def estimate_voc(photocurrent, saturation_current, nNsVth):
58
58
 
59
59
  def bishop88(diode_voltage, photocurrent, saturation_current,
60
60
  resistance_series, resistance_shunt, nNsVth, d2mutau=0,
61
- NsVbi=np.Inf, breakdown_factor=0., breakdown_voltage=-5.5,
61
+ NsVbi=np.inf, breakdown_factor=0., breakdown_voltage=-5.5,
62
62
  breakdown_exp=3.28, gradients=False):
63
63
  r"""
64
64
  Explicit calculation of points on the IV curve described by the single
@@ -206,7 +206,7 @@ def bishop88(diode_voltage, photocurrent, saturation_current,
206
206
 
207
207
  def bishop88_i_from_v(voltage, photocurrent, saturation_current,
208
208
  resistance_series, resistance_shunt, nNsVth,
209
- d2mutau=0, NsVbi=np.Inf, breakdown_factor=0.,
209
+ d2mutau=0, NsVbi=np.inf, breakdown_factor=0.,
210
210
  breakdown_voltage=-5.5, breakdown_exp=3.28,
211
211
  method='newton', method_kwargs=None):
212
212
  """
@@ -285,6 +285,12 @@ def bishop88_i_from_v(voltage, photocurrent, saturation_current,
285
285
 
286
286
  >>> i, method_output = bishop88_i_from_v(0.0, **args, method='newton',
287
287
  ... method_kwargs={'full_output': True})
288
+
289
+ References
290
+ ----------
291
+ .. [1] "Computer simulation of the effects of electrical mismatches in
292
+ photovoltaic cell interconnection circuits" JW Bishop, Solar Cell (1988)
293
+ :doi:`10.1016/0379-6787(88)90059-2`
288
294
  """
289
295
  # collect args
290
296
  args = (photocurrent, saturation_current,
@@ -304,6 +310,9 @@ def bishop88_i_from_v(voltage, photocurrent, saturation_current,
304
310
  if method == 'brentq':
305
311
  # first bound the search using voc
306
312
  voc_est = estimate_voc(photocurrent, saturation_current, nNsVth)
313
+ # start iteration slightly less than NsVbi when voc_est > NsVbi, to
314
+ # avoid the asymptote at NsVbi
315
+ xp = np.where(voc_est < NsVbi, voc_est, 0.9999*NsVbi)
307
316
 
308
317
  # brentq only works with scalar inputs, so we need a set up function
309
318
  # and np.vectorize to repeatedly call the optimizer with the right
@@ -317,7 +326,7 @@ def bishop88_i_from_v(voltage, photocurrent, saturation_current,
317
326
  **method_kwargs)
318
327
 
319
328
  vd_from_brent_vectorized = np.vectorize(vd_from_brent)
320
- vd = vd_from_brent_vectorized(voc_est, voltage, *args)
329
+ vd = vd_from_brent_vectorized(xp, voltage, *args)
321
330
  elif method == 'newton':
322
331
  x0, (voltage, *args), method_kwargs = \
323
332
  _prepare_newton_inputs(voltage, (voltage, *args), method_kwargs)
@@ -338,7 +347,7 @@ def bishop88_i_from_v(voltage, photocurrent, saturation_current,
338
347
 
339
348
  def bishop88_v_from_i(current, photocurrent, saturation_current,
340
349
  resistance_series, resistance_shunt, nNsVth,
341
- d2mutau=0, NsVbi=np.Inf, breakdown_factor=0.,
350
+ d2mutau=0, NsVbi=np.inf, breakdown_factor=0.,
342
351
  breakdown_voltage=-5.5, breakdown_exp=3.28,
343
352
  method='newton', method_kwargs=None):
344
353
  """
@@ -417,6 +426,12 @@ def bishop88_v_from_i(current, photocurrent, saturation_current,
417
426
 
418
427
  >>> v, method_output = bishop88_v_from_i(0.0, **args, method='newton',
419
428
  ... method_kwargs={'full_output': True})
429
+
430
+ References
431
+ ----------
432
+ .. [1] "Computer simulation of the effects of electrical mismatches in
433
+ photovoltaic cell interconnection circuits" JW Bishop, Solar Cell (1988)
434
+ :doi:`10.1016/0379-6787(88)90059-2`
420
435
  """
421
436
  # collect args
422
437
  args = (photocurrent, saturation_current,
@@ -431,6 +446,9 @@ def bishop88_v_from_i(current, photocurrent, saturation_current,
431
446
 
432
447
  # first bound the search using voc
433
448
  voc_est = estimate_voc(photocurrent, saturation_current, nNsVth)
449
+ # start iteration slightly less than NsVbi when voc_est > NsVbi, to avoid
450
+ # the asymptote at NsVbi
451
+ xp = np.where(voc_est < NsVbi, voc_est, 0.9999*NsVbi)
434
452
 
435
453
  def fi(x, i, *a):
436
454
  # calculate current residual given diode voltage "x"
@@ -449,10 +467,10 @@ def bishop88_v_from_i(current, photocurrent, saturation_current,
449
467
  **method_kwargs)
450
468
 
451
469
  vd_from_brent_vectorized = np.vectorize(vd_from_brent)
452
- vd = vd_from_brent_vectorized(voc_est, current, *args)
470
+ vd = vd_from_brent_vectorized(xp, current, *args)
453
471
  elif method == 'newton':
454
472
  x0, (current, *args), method_kwargs = \
455
- _prepare_newton_inputs(voc_est, (current, *args), method_kwargs)
473
+ _prepare_newton_inputs(xp, (current, *args), method_kwargs)
456
474
  vd = newton(func=lambda x, *a: fi(x, current, *a), x0=x0,
457
475
  fprime=lambda x, *a: bishop88(x, *a, gradients=True)[3],
458
476
  args=args, **method_kwargs)
@@ -469,7 +487,7 @@ def bishop88_v_from_i(current, photocurrent, saturation_current,
469
487
 
470
488
 
471
489
  def bishop88_mpp(photocurrent, saturation_current, resistance_series,
472
- resistance_shunt, nNsVth, d2mutau=0, NsVbi=np.Inf,
490
+ resistance_shunt, nNsVth, d2mutau=0, NsVbi=np.inf,
473
491
  breakdown_factor=0., breakdown_voltage=-5.5,
474
492
  breakdown_exp=3.28, method='newton', method_kwargs=None):
475
493
  """
@@ -547,6 +565,12 @@ def bishop88_mpp(photocurrent, saturation_current, resistance_series,
547
565
 
548
566
  >>> (i_mp, v_mp, p_mp), method_output = bishop88_mpp(**args,
549
567
  ... method='newton', method_kwargs={'full_output': True})
568
+
569
+ References
570
+ ----------
571
+ .. [1] "Computer simulation of the effects of electrical mismatches in
572
+ photovoltaic cell interconnection circuits" JW Bishop, Solar Cell (1988)
573
+ :doi:`10.1016/0379-6787(88)90059-2`
550
574
  """
551
575
  # collect args
552
576
  args = (photocurrent, saturation_current,
@@ -561,6 +585,9 @@ def bishop88_mpp(photocurrent, saturation_current, resistance_series,
561
585
 
562
586
  # first bound the search using voc
563
587
  voc_est = estimate_voc(photocurrent, saturation_current, nNsVth)
588
+ # start iteration slightly less than NsVbi when voc_est > NsVbi, to avoid
589
+ # the asymptote at NsVbi
590
+ xp = np.where(voc_est < NsVbi, voc_est, 0.9999*NsVbi)
564
591
 
565
592
  def fmpp(x, *a):
566
593
  return bishop88(x, *a, gradients=True)[6]
@@ -574,12 +601,13 @@ def bishop88_mpp(photocurrent, saturation_current, resistance_series,
574
601
  vbr_a, vbr, vbr_exp),
575
602
  **method_kwargs)
576
603
  )
577
- vd = vec_fun(voc_est, *args)
604
+ vd = vec_fun(xp, *args)
578
605
  elif method == 'newton':
579
606
  # make sure all args are numpy arrays if max size > 1
580
607
  # if voc_est is an array, then make a copy to use for initial guess, v0
608
+
581
609
  x0, args, method_kwargs = \
582
- _prepare_newton_inputs(voc_est, args, method_kwargs)
610
+ _prepare_newton_inputs(xp, args, method_kwargs)
583
611
  vd = newton(func=fmpp, x0=x0,
584
612
  fprime=lambda x, *a: bishop88(x, *a, gradients=True)[7],
585
613
  args=args, **method_kwargs)
pvlib/snow.py CHANGED
@@ -222,7 +222,9 @@ def loss_townsend(snow_total, snow_events, surface_tilt, relative_humidity,
222
222
  string_factor=1.0, angle_of_repose=40):
223
223
  '''
224
224
  Calculates monthly snow loss based on the Townsend monthly snow loss
225
- model [1]_.
225
+ model.
226
+
227
+ This model is described in [1]_.
226
228
 
227
229
  Parameters
228
230
  ----------
@@ -6,6 +6,7 @@ import pvlib
6
6
  import numpy as np
7
7
  import pandas as pd
8
8
  from scipy.interpolate import interp1d
9
+ from scipy.integrate import trapezoid
9
10
  import os
10
11
 
11
12
  from warnings import warn
@@ -224,7 +225,7 @@ def calc_spectral_mismatch_field(sr, e_sun, e_ref=None):
224
225
 
225
226
  # a helper function to make usable fraction calculations more readable
226
227
  def integrate(e):
227
- return np.trapz(e, x=e.T.index, axis=-1)
228
+ return trapezoid(e, x=e.T.index, axis=-1)
228
229
 
229
230
  # calculate usable fractions
230
231
  uf_sun = integrate(e_sun * sr_sun) / integrate(e_sun)
@@ -6,6 +6,7 @@ import pytest
6
6
  from pvlib.bifacial import utils
7
7
  from pvlib.shading import masking_angle, ground_angle
8
8
  from pvlib.tools import cosd
9
+ from scipy.integrate import trapezoid
9
10
 
10
11
 
11
12
  @pytest.fixture
@@ -99,7 +100,7 @@ def test_vf_ground_sky_2d_integ(test_system_fixed_tilt, vectorize):
99
100
  vf_integ = utils.vf_ground_sky_2d_integ(
100
101
  ts['rotation'], ts['gcr'], ts['height'], ts['pitch'],
101
102
  max_rows=1, npoints=3, vectorize=vectorize)
102
- expected_vf_integ = np.trapz(vfs_gnd_sky, pts, axis=0)
103
+ expected_vf_integ = trapezoid(vfs_gnd_sky, pts, axis=0)
103
104
  assert np.isclose(vf_integ, expected_vf_integ, rtol=0.1)
104
105
 
105
106
 
@@ -134,7 +135,7 @@ def test_vf_row_sky_2d_integ(test_system_fixed_tilt):
134
135
  x = np.arange(fx0[1], fx1[1], 1e-4)
135
136
  phi_y = masking_angle(ts['surface_tilt'], ts['gcr'], x)
136
137
  y = 0.5 * (1 + cosd(ts['surface_tilt'] + phi_y))
137
- y1 = np.trapz(y, x) / (fx1[1] - fx0[1])
138
+ y1 = trapezoid(y, x) / (fx1[1] - fx0[1])
138
139
  expected = np.array([y0, y1])
139
140
  assert np.allclose(vf, expected, rtol=1e-3)
140
141
  # with defaults (0, 1)
@@ -142,7 +143,7 @@ def test_vf_row_sky_2d_integ(test_system_fixed_tilt):
142
143
  x = np.arange(0, 1, 1e-4)
143
144
  phi_y = masking_angle(ts['surface_tilt'], ts['gcr'], x)
144
145
  y = 0.5 * (1 + cosd(ts['surface_tilt'] + phi_y))
145
- y1 = np.trapz(y, x) / (1 - 0)
146
+ y1 = trapezoid(y, x) / (1 - 0)
146
147
  assert np.allclose(vf, y1, rtol=1e-3)
147
148
 
148
149
 
@@ -179,7 +180,7 @@ def test_vf_ground_2d_integ(test_system_fixed_tilt):
179
180
  x = np.arange(fx0[1], fx1[1], 1e-4)
180
181
  phi_y = ground_angle(ts['surface_tilt'], ts['gcr'], x)
181
182
  y = 0.5 * (1 - cosd(phi_y - ts['surface_tilt']))
182
- y1 = np.trapz(y, x) / (fx1[1] - fx0[1])
183
+ y1 = trapezoid(y, x) / (fx1[1] - fx0[1])
183
184
  expected = np.array([y0, y1])
184
185
  assert np.allclose(vf, expected, rtol=1e-2)
185
186
  # with defaults (0, 1)
@@ -187,5 +188,5 @@ def test_vf_ground_2d_integ(test_system_fixed_tilt):
187
188
  x = np.arange(0, 1, 1e-4)
188
189
  phi_y = ground_angle(ts['surface_tilt'], ts['gcr'], x)
189
190
  y = 0.5 * (1 - cosd(phi_y - ts['surface_tilt']))
190
- y1 = np.trapz(y, x) / (1 - 0)
191
+ y1 = trapezoid(y, x) / (1 - 0)
191
192
  assert np.allclose(vf, y1, rtol=1e-2)
@@ -103,82 +103,57 @@ def test_PVSystem_get_iam_invalid(sapm_module_params, mocker):
103
103
  system.get_iam(45, iam_model='not_a_model')
104
104
 
105
105
 
106
- def test_retrieve_sam_raise_no_parameters():
106
+ def test_retrieve_sam_raises_exceptions():
107
107
  """
108
- Raise an exception if no parameters are provided to `retrieve_sam()`.
108
+ Raise an exception if an invalid parameter is provided to `retrieve_sam()`.
109
109
  """
110
- with pytest.raises(ValueError) as error:
110
+ with pytest.raises(ValueError, match="Please provide either"):
111
111
  pvsystem.retrieve_sam()
112
- assert 'A name or path must be provided!' == str(error.value)
113
-
114
-
115
- def test_retrieve_sam_cecmod():
116
- """
117
- Test the expected data is retrieved from the CEC module database. In
118
- particular, check for a known module in the database and check for the
119
- expected keys for that module.
120
- """
121
- data = pvsystem.retrieve_sam('cecmod')
122
- keys = [
123
- 'BIPV',
124
- 'Date',
125
- 'T_NOCT',
126
- 'A_c',
127
- 'N_s',
128
- 'I_sc_ref',
129
- 'V_oc_ref',
130
- 'I_mp_ref',
131
- 'V_mp_ref',
132
- 'alpha_sc',
133
- 'beta_oc',
134
- 'a_ref',
135
- 'I_L_ref',
136
- 'I_o_ref',
137
- 'R_s',
138
- 'R_sh_ref',
139
- 'Adjust',
140
- 'gamma_r',
141
- 'Version',
142
- 'STC',
143
- 'PTC',
144
- 'Technology',
145
- 'Bifacial',
146
- 'Length',
147
- 'Width',
148
- ]
149
- module = 'Itek_Energy_LLC_iT_300_HE'
150
- assert module in data
151
- assert set(data[module].keys()) == set(keys)
152
-
112
+ with pytest.raises(ValueError, match="Please provide either.*, not both."):
113
+ pvsystem.retrieve_sam(name="this_surely_wont_work", path="wont_work")
114
+ with pytest.raises(KeyError, match="Invalid name"):
115
+ pvsystem.retrieve_sam(name="this_surely_wont_work")
116
+ with pytest.raises(FileNotFoundError):
117
+ pvsystem.retrieve_sam(path="this_surely_wont_work.csv")
118
+
119
+
120
+ def test_retrieve_sam_databases():
121
+ """Test the expected keys are retrieved from each database."""
122
+ keys_per_database = {
123
+ "cecmod": {'Technology', 'Bifacial', 'STC', 'PTC', 'A_c', 'Length',
124
+ 'Width', 'N_s', 'I_sc_ref', 'V_oc_ref', 'I_mp_ref',
125
+ 'V_mp_ref', 'alpha_sc', 'beta_oc', 'T_NOCT', 'a_ref',
126
+ 'I_L_ref', 'I_o_ref', 'R_s', 'R_sh_ref', 'Adjust',
127
+ 'gamma_r', 'BIPV', 'Version', 'Date'},
128
+ "sandiamod": {'Vintage', 'Area', 'Material', 'Cells_in_Series',
129
+ 'Parallel_Strings', 'Isco', 'Voco', 'Impo', 'Vmpo',
130
+ 'Aisc', 'Aimp', 'C0', 'C1', 'Bvoco', 'Mbvoc', 'Bvmpo',
131
+ 'Mbvmp', 'N', 'C2', 'C3', 'A0', 'A1', 'A2', 'A3', 'A4',
132
+ 'B0', 'B1', 'B2', 'B3', 'B4', 'B5', 'DTC', 'FD', 'A',
133
+ 'B', 'C4', 'C5', 'IXO', 'IXXO', 'C6', 'C7', 'Notes'},
134
+ "adrinverter": {'Manufacturer', 'Model', 'Source', 'Vac', 'Vintage',
135
+ 'Pacmax', 'Pnom', 'Vnom', 'Vmin', 'Vmax',
136
+ 'ADRCoefficients', 'Pnt', 'Vdcmax', 'Idcmax',
137
+ 'MPPTLow', 'MPPTHi', 'TambLow', 'TambHi', 'Weight',
138
+ 'PacFitErrMax', 'YearOfData'},
139
+ "cecinverter": {'Vac', 'Paco', 'Pdco', 'Vdco', 'Pso', 'C0', 'C1', 'C2',
140
+ 'C3', 'Pnt', 'Vdcmax', 'Idcmax', 'Mppt_low',
141
+ 'Mppt_high', 'CEC_Date', 'CEC_Type'}
142
+ } # fmt: skip
143
+ item_per_database = {
144
+ "cecmod": "Itek_Energy_LLC_iT_300_HE",
145
+ "sandiamod": "Canadian_Solar_CS6X_300M__2013_",
146
+ "adrinverter": "Sainty_Solar__SSI_4K4U_240V__CEC_2011_",
147
+ "cecinverter": "ABB__PVI_3_0_OUTD_S_US__208V_",
148
+ }
149
+ # duplicate the cecinverter items for sandiainverter, for backwards compat
150
+ keys_per_database["sandiainverter"] = keys_per_database["cecinverter"]
151
+ item_per_database["sandiainverter"] = item_per_database["cecinverter"]
153
152
 
154
- def test_retrieve_sam_cecinverter():
155
- """
156
- Test the expected data is retrieved from the CEC inverter database. In
157
- particular, check for a known inverter in the database and check for the
158
- expected keys for that inverter.
159
- """
160
- data = pvsystem.retrieve_sam('cecinverter')
161
- keys = [
162
- 'Vac',
163
- 'Paco',
164
- 'Pdco',
165
- 'Vdco',
166
- 'Pso',
167
- 'C0',
168
- 'C1',
169
- 'C2',
170
- 'C3',
171
- 'Pnt',
172
- 'Vdcmax',
173
- 'Idcmax',
174
- 'Mppt_low',
175
- 'Mppt_high',
176
- 'CEC_Date',
177
- 'CEC_Type',
178
- ]
179
- inverter = 'Yaskawa_Solectria_Solar__PVI_5300_208__208V_'
180
- assert inverter in data
181
- assert set(data[inverter].keys()) == set(keys)
153
+ for database in keys_per_database.keys():
154
+ data = pvsystem.retrieve_sam(database)
155
+ assert set(data.index) == keys_per_database[database]
156
+ assert item_per_database[database] in data.columns
182
157
 
183
158
 
184
159
  def test_sapm(sapm_module_params):
@@ -191,16 +166,14 @@ def test_sapm(sapm_module_params):
191
166
  out = pvsystem.sapm(effective_irradiance, temp_cell, sapm_module_params)
192
167
 
193
168
  expected = pd.DataFrame(np.array(
194
- [[ -5.0608322 , -4.65037767, nan, nan,
195
- nan, -4.91119927, -4.15367716],
196
- [ 2.545575 , 2.28773882, 56.86182059, 47.21121608,
197
- 108.00693168, 2.48357383, 1.71782772],
198
- [ 5.65584763, 5.01709903, 54.1943277 , 42.51861718,
199
- 213.32011294, 5.52987899, 3.48660728],
200
- [ nan, nan, nan, nan,
201
- nan, nan, nan],
202
- [ nan, nan, nan, nan,
203
- nan, nan, nan]]),
169
+ [[-5.0608322, -4.65037767, np.nan, np.nan, np.nan,
170
+ -4.91119927, -4.16721569],
171
+ [2.545575, 2.28773882, 56.86182059, 47.21121608, 108.00693168,
172
+ 2.48357383, 1.71782772],
173
+ [5.65584763, 5.01709903, 54.1943277, 42.51861718, 213.32011294,
174
+ 5.52987899, 3.46796463],
175
+ [np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan],
176
+ [np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan]]),
204
177
  columns=['i_sc', 'i_mp', 'v_oc', 'v_mp', 'p_mp', 'i_x', 'i_xx'],
205
178
  index=times)
206
179
 
@@ -209,13 +182,13 @@ def test_sapm(sapm_module_params):
209
182
  out = pvsystem.sapm(1000, 25, sapm_module_params)
210
183
 
211
184
  expected = OrderedDict()
212
- expected['i_sc'] = 5.09115
213
- expected['i_mp'] = 4.5462909092579995
214
- expected['v_oc'] = 59.260800000000003
215
- expected['v_mp'] = 48.315600000000003
216
- expected['p_mp'] = 219.65677305534581
217
- expected['i_x'] = 4.9759899999999995
218
- expected['i_xx'] = 3.1880204359100004
185
+ expected['i_sc'] = sapm_module_params['Isco']
186
+ expected['i_mp'] = sapm_module_params['Impo']
187
+ expected['v_oc'] = sapm_module_params['Voco']
188
+ expected['v_mp'] = sapm_module_params['Vmpo']
189
+ expected['p_mp'] = sapm_module_params['Impo'] * sapm_module_params['Vmpo']
190
+ expected['i_x'] = sapm_module_params['IXO']
191
+ expected['i_xx'] = sapm_module_params['IXXO']
219
192
 
220
193
  for k, v in expected.items():
221
194
  assert_allclose(out[k], v, atol=1e-4)
@@ -10,6 +10,7 @@ from pvlib.singlediode import (bishop88_mpp, estimate_voc, VOLTAGE_BUILTIN,
10
10
  bishop88, bishop88_i_from_v, bishop88_v_from_i)
11
11
  from pvlib._deprecation import pvlibDeprecationWarning
12
12
  import pytest
13
+ from numpy.testing import assert_array_equal
13
14
  from .conftest import DATA_DIR
14
15
 
15
16
  POA = 888
@@ -167,17 +168,24 @@ def test_singlediode_precision(method, precise_iv_curves):
167
168
  assert np.allclose(pc['i_xx'], outs['i_xx'], atol=1e-6, rtol=0)
168
169
 
169
170
 
170
- def test_singlediode_lambert_negative_voc():
171
-
172
- # Those values result in a negative v_oc out of `_lambertw_v_from_i`
173
- x = np.array([0., 1.480501e-11, 0.178, 8000., 1.797559])
174
- outs = pvsystem.singlediode(*x, method='lambertw')
175
- assert outs['v_oc'] == 0
171
+ def test_singlediode_lambert_negative_voc(mocker):
172
+ """Tests approximation to zero of v_oc when it is negative and small.
173
+ See singlediode.py:_lambertw > comment 'Set small elements <0 in v_oc to 0'
174
+ """
175
+ # Next values should result in a negative v_oc out of `_lambertw_v_from_i`
176
+ # however, we can't ensure that the output belongs to (-1e-12, 0), so we
177
+ # mock it. It depends on the platform and Python distro. See issue #2000.
178
+ patcher = mocker.patch("pvlib.singlediode._lambertw_v_from_i")
179
+ x = np.array([0.0, 1.480501e-11, 0.178, 8000.0, 1.797559])
180
+ patcher.return_value = -9.999e-13
181
+ outs = pvsystem.singlediode(*x, method="lambertw")
182
+ assert outs["v_oc"] == 0
176
183
 
177
184
  # Testing for an array
178
- x = np.array([x, x]).T
179
- outs = pvsystem.singlediode(*x, method='lambertw')
180
- assert np.array_equal(outs['v_oc'], [0, 0])
185
+ patcher.return_value = np.array([-9.999e-13, -1.001e-13])
186
+ x = np.array([x, x]).T
187
+ outs = pvsystem.singlediode(*x, method="lambertw")
188
+ assert_array_equal(outs["v_oc"], [0, 0])
181
189
 
182
190
 
183
191
  @pytest.mark.parametrize('method', ['lambertw'])
@@ -347,7 +355,7 @@ def test_pvsyst_recombination_loss(method, poa, temp_cell, expected, tol):
347
355
  # other conditions with breakdown model on and recombination model off
348
356
  (
349
357
  (1.e-4, -5.5, 3.28),
350
- (0., np.Inf),
358
+ (0., np.inf),
351
359
  POA,
352
360
  TCELL,
353
361
  {
@@ -567,3 +575,53 @@ def test_bishop88_pdSeries_len_one(method, bishop88_arguments):
567
575
  bishop88_i_from_v(pd.Series([0]), **bishop88_arguments, method=method)
568
576
  bishop88_v_from_i(pd.Series([0]), **bishop88_arguments, method=method)
569
577
  bishop88_mpp(**bishop88_arguments, method=method)
578
+
579
+
580
+ def _sde_check_solution(i, v, il, io, rs, rsh, a, d2mutau=0., NsVbi=np.inf):
581
+ vd = v + rs * i
582
+ return il - io*np.expm1(vd/a) - vd/rsh - il*d2mutau/(NsVbi - vd) - i
583
+
584
+
585
+ @pytest.mark.parametrize('method', ['newton', 'brentq'])
586
+ def test_bishop88_init_cond(method):
587
+ # GH 2013
588
+ p = {'alpha_sc': 0.0012256,
589
+ 'gamma_ref': 1.2916241612804187,
590
+ 'mu_gamma': 0.00047308959960937403,
591
+ 'I_L_ref': 3.068717040806731,
592
+ 'I_o_ref': 2.2691248021217617e-11,
593
+ 'R_sh_ref': 7000,
594
+ 'R_sh_0': 7000,
595
+ 'R_s': 4.602,
596
+ 'cells_in_series': 268,
597
+ 'R_sh_exp': 5.5,
598
+ 'EgRef': 1.5}
599
+ NsVbi = 268 * 0.9
600
+ d2mutau = 1.4
601
+ irrad = np.arange(20, 1100, 20)
602
+ tc = np.arange(-25, 74, 1)
603
+ weather = np.array(np.meshgrid(irrad, tc)).T.reshape(-1, 2)
604
+ # with the above parameters and weather conditions, a few combinations
605
+ # result in voc_est > NsVbi, which causes failure of brentq and newton
606
+ # when the recombination parameters NsVbi and d2mutau are used.
607
+ sde_params = pvsystem.calcparams_pvsyst(weather[:, 0], weather[:, 1], **p)
608
+ # test _mpp
609
+ result = bishop88_mpp(*sde_params, d2mutau=d2mutau, NsVbi=NsVbi)
610
+ imp, vmp, pmp = result
611
+ err = np.abs(_sde_check_solution(
612
+ imp, vmp, sde_params[0], sde_params[1], sde_params[2], sde_params[3],
613
+ sde_params[4], d2mutau=d2mutau, NsVbi=NsVbi))
614
+ bad_results = np.isnan(pmp) | (pmp < 0) | (err > 0.00001) # 0.01mA error
615
+ assert not bad_results.any()
616
+ # test v_from_i
617
+ vmp2 = bishop88_v_from_i(imp, *sde_params, d2mutau=d2mutau, NsVbi=NsVbi)
618
+ err = np.abs(_sde_check_solution(imp, vmp2, *sde_params, d2mutau=d2mutau,
619
+ NsVbi=NsVbi))
620
+ bad_results = np.isnan(vmp2) | (vmp2 < 0) | (err > 0.00001)
621
+ assert not bad_results.any()
622
+ # test v_from_i
623
+ imp2 = bishop88_i_from_v(vmp, *sde_params, d2mutau=d2mutau, NsVbi=NsVbi)
624
+ err = np.abs(_sde_check_solution(imp2, vmp, *sde_params, d2mutau=d2mutau,
625
+ NsVbi=NsVbi))
626
+ bad_results = np.isnan(imp2) | (imp2 < 0) | (err > 0.00001)
627
+ assert not bad_results.any()
pvlib/version.py CHANGED
@@ -1,8 +1,4 @@
1
- try:
2
- from importlib.metadata import PackageNotFoundError, version
3
- except ImportError:
4
- # for python < 3.8
5
- from importlib_metadata import PackageNotFoundError, version
1
+ from importlib.metadata import PackageNotFoundError, version
6
2
 
7
3
  try:
8
4
  __version__ = version(__package__)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pvlib
3
- Version: 0.10.4
3
+ Version: 0.10.5
4
4
  Summary: A set of functions and classes for simulating the performance of photovoltaic energy systems.
5
5
  Home-page: https://github.com/pvlib/pvlib-python
6
6
  Author-email: pvlib python Developers <pvlib-admin@googlegroups.com>
@@ -15,7 +15,7 @@ Classifier: Intended Audience :: Science/Research
15
15
  Classifier: Programming Language :: Python
16
16
  Classifier: Programming Language :: Python :: 3
17
17
  Classifier: Topic :: Scientific/Engineering
18
- Requires-Python: >=3.7
18
+ Requires-Python: >=3.8
19
19
  Description-Content-Type: text/x-rst
20
20
  License-File: LICENSE
21
21
  License-File: AUTHORS.md
@@ -23,9 +23,8 @@ Requires-Dist: numpy >=1.17.3
23
23
  Requires-Dist: pandas >=1.3.0
24
24
  Requires-Dist: pytz
25
25
  Requires-Dist: requests
26
- Requires-Dist: scipy >=1.5.0
26
+ Requires-Dist: scipy >=1.6.0
27
27
  Requires-Dist: h5py
28
- Requires-Dist: importlib-metadata ; python_version < "3.8"
29
28
  Provides-Extra: all
30
29
  Requires-Dist: pvlib[doc,optional,test] ; extra == 'all'
31
30
  Provides-Extra: doc
@@ -5,25 +5,25 @@ pvlib/clearsky.py,sha256=uB26zFv914f2BAWvo33sUESbNaWydaU28CfvyCyd0FY,38289
5
5
  pvlib/iam.py,sha256=uYwdOaw5Brkl0d1WmueQG9XqL2eMJP_TZ2x7dQ5UxZo,44330
6
6
  pvlib/inverter.py,sha256=ZpSv3cjt-Qm_JundL_jkvhCUd3iGjmlKcnNJeJqA2Qw,19127
7
7
  pvlib/irradiance.py,sha256=HNZ5N71FGcz7-Y4bqZDt8SB-CGKy5E7uVs6vOlPMyew,141985
8
- pvlib/location.py,sha256=tw81lPq50XNtKgmEN27BeHQT2K4ObyRkh4RfgZSf0Tg,15363
8
+ pvlib/location.py,sha256=cHdX6m3aAZAY96DXCC7W-W6ExisB2sidY4tEqBMELJk,15455
9
9
  pvlib/modelchain.py,sha256=f-6mSWVqyjLNX6SW0fMx4zWwI4BMSwKXmxs1MAX0e04,79453
10
- pvlib/pvarray.py,sha256=k2RkTN0Ce04pydl8ZuzRhJYlco26PNMHb15dd0fjSss,12695
11
- pvlib/pvsystem.py,sha256=4oBnRY50cZfegjLQMBMKu7tAAgjIXYQEv36jGN0RmsA,109241
12
- pvlib/scaling.py,sha256=oCAY7pfoeUWBd7oUuI8x146YecXDREsCmqrkGQ2yzFc,10953
10
+ pvlib/pvarray.py,sha256=r60sGTxFNlPiFQndusCJmlEIPX0dv9_7ozKw8zxh7IM,12677
11
+ pvlib/pvsystem.py,sha256=6jF0iXatWhVU_vVgcWhIFgKwqJ7sksCCx42spG2yXv8,109775
12
+ pvlib/scaling.py,sha256=SsQEmM4f4O1wC7e0amEV4SgaRTBX8nG5IiSV9Xs0i5o,10983
13
13
  pvlib/shading.py,sha256=P6GmKxHXQGF0oCqDNN-2NjsvYHqpGG5GzRpepOAXhTk,12495
14
- pvlib/singlediode.py,sha256=PPvTODA8Q92u--rlQDNKBGeKVHmxqZVCkvw5xEfiYWA,34229
15
- pvlib/snow.py,sha256=it95wI8pbyBy9xSdpuPTylzE1OXQwf73FtFbbSrHt5g,12731
14
+ pvlib/singlediode.py,sha256=Bsr4YlTFBcR1kIIgMbL-QelO5YF-20c2kJjSyql2FYs,35399
15
+ pvlib/snow.py,sha256=LYFEpU5AnP82o6q5v6kQfgopkYtHO-aEyYFV9knpNvM,12764
16
16
  pvlib/soiling.py,sha256=zDJ3N0uyeS1CoO0mxSdG16q2FCBLZSHbujJHgish54U,8799
17
17
  pvlib/solarposition.py,sha256=FFafBzWYdLgNOsJiQY4l1LuqTn1-TYMvgoaLW2bQstI,50502
18
18
  pvlib/spa.py,sha256=fTHdkU44M2d8hG9_i2MuBdDsqlgERBwVnsEMMPYLCuo,44802
19
19
  pvlib/temperature.py,sha256=cNdbMx_x38XK5YwyxdWVBlnKkfXDBSjb9X_KTHY2hV8,55424
20
20
  pvlib/tools.py,sha256=S3TswC_biexLSL8BlNdcLlWNVYSs7nG3EJhUEbHh59E,12650
21
21
  pvlib/tracking.py,sha256=fwssoO_9vi5_aLBl59G0KE_EmsB3Jt0yIJlllFcpb5s,15802
22
- pvlib/version.py,sha256=9b2gyX4rmKu60DCgjOhhiEQSF9sD5utxNUJ3NSftRWs,282
22
+ pvlib/version.py,sha256=0CONzyOSN34Jgbaj9JzemFuaEnbRON_yxp-ah6_KxxQ,165
23
23
  pvlib/bifacial/__init__.py,sha256=8uOiQ8cR0Wp62F-dLW25b1_xI3AxhwWlNagXqMyZUqA,412
24
24
  pvlib/bifacial/infinite_sheds.py,sha256=rbiluCon6Tqpa_FizUfk5zBc6tH3ubk7xRqRAXp2Xq0,23051
25
25
  pvlib/bifacial/pvfactors.py,sha256=QJXqjok4UcaUToNs6eR5ZDMsVf3HHT2AqW2u36hOOSI,5437
26
- pvlib/bifacial/utils.py,sha256=SHdisvAisrrZvy7yI9phszHFWJxqby9pOEwE2lpsaTI,14503
26
+ pvlib/bifacial/utils.py,sha256=Q2KSzn-vltO13QHYEfLVEWkTqed8Q8f_Eu4tlyrK2Ts,14542
27
27
  pvlib/data/12839.tm2,sha256=6v86FhwMJeUJIEx8Mj9Rqp_OqmeaQ3rpObunQVaM6ss,1261501
28
28
  pvlib/data/703165TY.csv,sha256=8DM6aKEW9a6S8ShaKrh4TY4A5So2dEVlisiNctk9jKQ,1760582
29
29
  pvlib/data/723170TYA.CSV,sha256=Hpb4RjjOmOaykAK8RaJ6ppuymw7QNo07Urex-BYQxsk,1716576
@@ -106,8 +106,8 @@ pvlib/iotools/solaranywhere.py,sha256=_kDetQ0R8rQgcfTZjeQArq9nmCtVa4upF_KGrcipov
106
106
  pvlib/iotools/solargis.py,sha256=6FeIsqs_bs2oNrUGvkv7Dc4AlIsDiwpCs5oFVcBheO8,8274
107
107
  pvlib/iotools/solcast.py,sha256=d-2LAC-Tlazmih_QZKYbOKCyZaP7U08pIwoKTfciTCk,15332
108
108
  pvlib/iotools/solrad.py,sha256=M8Xwasro6_hFiZP7hcsYSeEze3q5kNmnV0kAdNHqgBI,7177
109
- pvlib/iotools/srml.py,sha256=I3Q-GWIUcc4yrTz2WvfdAi3tUy0QBH1vjV-WrIsk3rw,10833
110
- pvlib/iotools/surfrad.py,sha256=NAaEH77nmgNgpNhTk1OFYdcVHUET5QsbQg9byx5_0Yw,7349
109
+ pvlib/iotools/srml.py,sha256=XRbq1vf1D3XCl2vMC9YHeuYdoFsjYqcu-r4voIvsMiA,10838
110
+ pvlib/iotools/surfrad.py,sha256=WFh2__FGlOwHg6RTxIkcMmdMucX0vbQfHEz9q_HLGjY,7349
111
111
  pvlib/iotools/tmy.py,sha256=-lxHnehZ2FnblM_28KYPG4FWd_rnDXIHv_dHJz092K0,30719
112
112
  pvlib/ivtools/__init__.py,sha256=bnUDPqkzCP96CaFFK3Gw4HNczJoHtO-cI9GBGAtZVGI,159
113
113
  pvlib/ivtools/sde.py,sha256=HL2oE70Ls7xccikyaUSi6SQKx3cWES5XoaMAGuMjPIw,17008
@@ -120,7 +120,7 @@ pvlib/spa_c_files/setup.py,sha256=RcMEf0R2wKHJjvpUH5y6h22m86y6UrdXwkPkHKNme48,11
120
120
  pvlib/spa_c_files/spa_py.pyx,sha256=XMjlxfcSPM2nXTWVbyGme0HFBvPhOxRFuQEnbhQfT3Q,809
121
121
  pvlib/spa_c_files/spa_py_example.py,sha256=p3ms0mhLycAuZJyaE3Wageqnd_56zh2EKxXK-jlTJfg,1179
122
122
  pvlib/spectrum/__init__.py,sha256=Xtu6PejkWxUuJSkmXjdsAQJn1GUj4HmRGlOmGZbqUL8,286
123
- pvlib/spectrum/mismatch.py,sha256=wzy6WULWmjcu2Y5LVPw-db4EmKjxhhFbrAeItiPV_Ng,22608
123
+ pvlib/spectrum/mismatch.py,sha256=VvTv6iklE8eKTaZ3SMrrh8_JE7s8eBjFhPNy-uC40sM,22647
124
124
  pvlib/spectrum/spectrl2.py,sha256=gJiHlJrmxHQkqWDVY2htU3hihFvt9JDvY3QZeL0FkyQ,18964
125
125
  pvlib/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
126
126
  pvlib/tests/conftest.py,sha256=gqTLfGacGrfSYhhRCRkfjXQgdr50KfuwliZWQvPQfNc,13217
@@ -134,10 +134,10 @@ pvlib/tests/test_location.py,sha256=UhGawiOEdXIcym_kVC8wbxZULuqU3MzZ3k_3Zgzkl9Y,
134
134
  pvlib/tests/test_modelchain.py,sha256=vaCCtALPaB1FWtC9Iw3ty3vctqyAVvdxSkvIt6OFsH8,89421
135
135
  pvlib/tests/test_numerical_precision.py,sha256=hu9ebaykI3WxZhE1SOzbw0zjjcYjg79-T5oGQlBNzXo,4331
136
136
  pvlib/tests/test_pvarray.py,sha256=zAxaK-2jUPLRwgOlnPdpvgLeSHL7op_63XxSDzKup8s,2694
137
- pvlib/tests/test_pvsystem.py,sha256=19zkhCw__hMZRe4-Yhzanz6Uww1bTJlo2U4umT-10VM,98673
137
+ pvlib/tests/test_pvsystem.py,sha256=eFlc0UeqwFu-Etf81kiohAUW5ZohKgyvgfenqCMb45o,99567
138
138
  pvlib/tests/test_scaling.py,sha256=KlzMAiZcpWHLega4JJIBUy5PbzworWm9tqjLFaqoFcg,6832
139
139
  pvlib/tests/test_shading.py,sha256=QH6wb0wAE3DGhaNUnhQLlknEmz_EL_tRTUe25yyPZ1Y,7846
140
- pvlib/tests/test_singlediode.py,sha256=Jezj89iOJZUGlBRJG1WOoG09q99mdoboibXu3hgqAcw,22505
140
+ pvlib/tests/test_singlediode.py,sha256=qnSRMO_iD6qz2mKQxX0hkqOKQSGrNo0hWdlWj9M58zo,25191
141
141
  pvlib/tests/test_snow.py,sha256=YyPpF-_VwNadrsuUzv32UgRlzZHEDxSYpciLNga16P0,8590
142
142
  pvlib/tests/test_soiling.py,sha256=QepAr_jVS24l07EUx8rrTjG67t7_vltJ1si_MlOXAGE,8183
143
143
  pvlib/tests/test_solarposition.py,sha256=K4_EOZ4arSHRxbdiytjalANLQadASE4zFSpmTAr4QOg,41652
@@ -149,7 +149,7 @@ pvlib/tests/test_tracking.py,sha256=tqnVv3wGagJetly9qwJFstuMHAiakweTi31sR0VZbSU,
149
149
  pvlib/tests/bifacial/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
150
150
  pvlib/tests/bifacial/test_infinite_sheds.py,sha256=wYuJ8U7gEiG-lg0L3j2NaGOG6NhQWB2ZAUnrffH-n0Y,13549
151
151
  pvlib/tests/bifacial/test_pvfactors.py,sha256=vocfxIsBAZwaEeRDfRAZmvemuYIRXI0UVbuKqUXRU6g,3144
152
- pvlib/tests/bifacial/test_utils.py,sha256=B-yl3RGIVCyjTjoB5pq88QUIUgUyVz6f_XikkevqbCY,8303
152
+ pvlib/tests/bifacial/test_utils.py,sha256=c6Q9H_3pocHDNokxq26HCPiyoNvZGS1h9FmSLrWPPh4,8346
153
153
  pvlib/tests/iotools/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
154
154
  pvlib/tests/iotools/test_acis.py,sha256=Ya1CzAcQDzUWFaVZduiE_rGfx7RBbQtxajW4ekfWIWE,8440
155
155
  pvlib/tests/iotools/test_bsrn.py,sha256=7DHT6CcEGWZ_qNsLXDSSF_Rk6hpa1zqgNnvpnK_T8_k,4781
@@ -171,9 +171,9 @@ pvlib/tests/ivtools/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSu
171
171
  pvlib/tests/ivtools/test_sde.py,sha256=dBJkk9tWskwc6Iyoziar9MoZESrOSkepOk51g5QOy1I,13844
172
172
  pvlib/tests/ivtools/test_sdm.py,sha256=5ioqsEJJE-JCSCGRLXj1zCuJzGIPNY622GyflJMU_MM,16406
173
173
  pvlib/tests/ivtools/test_utils.py,sha256=-BPEUgB5aCkJOv-apRkjeg0IraZ1Ebf5SmObk4Zusz4,6905
174
- pvlib-0.10.4.dist-info/AUTHORS.md,sha256=Fxk4p_lXlMeQ6g2A1-7oPrgpULDxuJuC9Ebc-3yyj_o,1474
175
- pvlib-0.10.4.dist-info/LICENSE,sha256=oC4S3araPPDV292K_91XfC7sZAdYqVhCowT3UTuMC-Q,1622
176
- pvlib-0.10.4.dist-info/METADATA,sha256=kzFfVDCHN5kNx-UjIbvCqMdVimg8f7On17gEOLdFX8k,2844
177
- pvlib-0.10.4.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
178
- pvlib-0.10.4.dist-info/top_level.txt,sha256=eq9CH6YXUc3Fh3dyQ5hQXoGYfSm1SYEAlMygyR22MgE,6
179
- pvlib-0.10.4.dist-info/RECORD,,
174
+ pvlib-0.10.5.dist-info/AUTHORS.md,sha256=Fxk4p_lXlMeQ6g2A1-7oPrgpULDxuJuC9Ebc-3yyj_o,1474
175
+ pvlib-0.10.5.dist-info/LICENSE,sha256=oC4S3araPPDV292K_91XfC7sZAdYqVhCowT3UTuMC-Q,1622
176
+ pvlib-0.10.5.dist-info/METADATA,sha256=cimQNDgoZe_S2_jiDXi0v2UfEVboTEyLIFY-EVqzaQU,2785
177
+ pvlib-0.10.5.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
178
+ pvlib-0.10.5.dist-info/top_level.txt,sha256=eq9CH6YXUc3Fh3dyQ5hQXoGYfSm1SYEAlMygyR22MgE,6
179
+ pvlib-0.10.5.dist-info/RECORD,,
File without changes