pvlib 0.11.1__py3-none-any.whl → 0.11.2__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/_deprecation.py +73 -0
- pvlib/atmosphere.py +79 -0
- pvlib/clearsky.py +35 -22
- pvlib/data/pvgis_tmy_test.csv +8761 -0
- pvlib/data/tmy_45.000_8.000_2005_2023.csv +8789 -0
- pvlib/data/tmy_45.000_8.000_2005_2023.epw +8768 -0
- pvlib/data/tmy_45.000_8.000_2005_2023.json +1 -0
- pvlib/data/tmy_45.000_8.000_2005_2023.txt +8761 -0
- pvlib/data/tmy_45.000_8.000_userhorizon.json +1 -1
- pvlib/iam.py +4 -4
- pvlib/iotools/midc.py +1 -1
- pvlib/iotools/pvgis.py +0 -10
- pvlib/irradiance.py +98 -55
- pvlib/ivtools/sdm.py +75 -52
- pvlib/pvsystem.py +132 -84
- pvlib/solarposition.py +46 -30
- pvlib/spa.py +4 -2
- pvlib/spectrum/irradiance.py +2 -1
- pvlib/spectrum/spectrl2.py +2 -1
- pvlib/temperature.py +49 -3
- pvlib/tests/iotools/test_pvgis.py +9 -9
- pvlib/tests/ivtools/test_sdm.py +23 -1
- pvlib/tests/test__deprecation.py +97 -0
- pvlib/tests/test_atmosphere.py +147 -0
- pvlib/tests/test_clearsky.py +7 -1
- pvlib/tests/test_conftest.py +0 -44
- pvlib/tests/test_irradiance.py +56 -10
- pvlib/tests/test_pvsystem.py +17 -1
- pvlib/tests/test_solarposition.py +33 -0
- pvlib/tests/test_spa.py +29 -0
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/METADATA +11 -10
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/RECORD +36 -37
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/WHEEL +1 -1
- pvlib/data/aod550_tcwv_20121101_test.nc +0 -0
- pvlib/data/pvgis_tmy_test.dat +0 -8761
- pvlib/data/tmy_45.000_8.000_2005_2020.csv +0 -8789
- pvlib/data/tmy_45.000_8.000_2005_2020.epw +0 -8768
- pvlib/data/tmy_45.000_8.000_2005_2020.json +0 -1
- pvlib/data/tmy_45.000_8.000_2005_2020.txt +0 -8761
- pvlib/data/variables_style_rules.csv +0 -56
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/AUTHORS.md +0 -0
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/LICENSE +0 -0
- {pvlib-0.11.1.dist-info → pvlib-0.11.2.dist-info}/top_level.txt +0 -0
pvlib/pvsystem.py
CHANGED
|
@@ -17,7 +17,7 @@ from dataclasses import dataclass
|
|
|
17
17
|
from abc import ABC, abstractmethod
|
|
18
18
|
from typing import Optional, Union
|
|
19
19
|
|
|
20
|
-
from pvlib._deprecation import deprecated
|
|
20
|
+
from pvlib._deprecation import deprecated
|
|
21
21
|
|
|
22
22
|
import pvlib # used to avoid albedo name collision in the Array class
|
|
23
23
|
from pvlib import (atmosphere, iam, inverter, irradiance,
|
|
@@ -104,22 +104,22 @@ class PVSystem:
|
|
|
104
104
|
----------
|
|
105
105
|
arrays : Array or iterable of Array, optional
|
|
106
106
|
An Array or list of arrays that are part of the system. If not
|
|
107
|
-
specified a single array is created from the other parameters (e.g.
|
|
107
|
+
specified, a single array is created from the other parameters (e.g.
|
|
108
108
|
`surface_tilt`, `surface_azimuth`). If specified as a list, the list
|
|
109
109
|
must contain at least one Array;
|
|
110
110
|
if length of arrays is 0 a ValueError is raised. If `arrays` is
|
|
111
111
|
specified the following PVSystem parameters are ignored:
|
|
112
112
|
|
|
113
|
-
-
|
|
114
|
-
-
|
|
115
|
-
-
|
|
116
|
-
-
|
|
117
|
-
-
|
|
118
|
-
-
|
|
119
|
-
-
|
|
120
|
-
-
|
|
121
|
-
-
|
|
122
|
-
-
|
|
113
|
+
- ``surface_tilt``
|
|
114
|
+
- ``surface_azimuth``
|
|
115
|
+
- ``albedo``
|
|
116
|
+
- ``surface_type``
|
|
117
|
+
- ``module``
|
|
118
|
+
- ``module_type``
|
|
119
|
+
- ``module_parameters``
|
|
120
|
+
- ``temperature_model_parameters``
|
|
121
|
+
- ``modules_per_string``
|
|
122
|
+
- ``strings_per_inverter``
|
|
123
123
|
|
|
124
124
|
surface_tilt: float or array-like, default 0
|
|
125
125
|
Surface tilt angles in decimal degrees.
|
|
@@ -127,7 +127,7 @@ class PVSystem:
|
|
|
127
127
|
(e.g. surface facing up = 0, surface facing horizon = 90)
|
|
128
128
|
|
|
129
129
|
surface_azimuth: float or array-like, default 180
|
|
130
|
-
Azimuth angle of the module surface.
|
|
130
|
+
Azimuth angle of the module surface in decimal degrees.
|
|
131
131
|
North=0, East=90, South=180, West=270.
|
|
132
132
|
|
|
133
133
|
albedo : float, optional
|
|
@@ -142,8 +142,6 @@ class PVSystem:
|
|
|
142
142
|
|
|
143
143
|
module : string, optional
|
|
144
144
|
The model name of the modules.
|
|
145
|
-
May be used to look up the module_parameters dictionary
|
|
146
|
-
via some other method.
|
|
147
145
|
|
|
148
146
|
module_type : string, default 'glass_polymer'
|
|
149
147
|
Describes the module's construction. Valid strings are 'glass_polymer'
|
|
@@ -154,7 +152,8 @@ class PVSystem:
|
|
|
154
152
|
|
|
155
153
|
temperature_model_parameters : dict or Series, optional
|
|
156
154
|
Temperature model parameters as required by one of the models in
|
|
157
|
-
pvlib.temperature (excluding poa_global
|
|
155
|
+
:py:mod:`pvlib.temperature` (excluding ``poa_global``, ``temp_air`` and
|
|
156
|
+
``wind_speed``).
|
|
158
157
|
|
|
159
158
|
modules_per_string: int or float, default 1
|
|
160
159
|
See system topology discussion above.
|
|
@@ -164,15 +163,17 @@ class PVSystem:
|
|
|
164
163
|
|
|
165
164
|
inverter : string, optional
|
|
166
165
|
The model name of the inverters.
|
|
167
|
-
May be used to look up the inverter_parameters dictionary
|
|
168
|
-
via some other method.
|
|
169
166
|
|
|
170
167
|
inverter_parameters : dict or Series, optional
|
|
171
168
|
Inverter parameters as defined by the SAPM, CEC, or other.
|
|
172
169
|
|
|
173
|
-
racking_model : string,
|
|
174
|
-
Valid strings are 'open_rack'
|
|
175
|
-
|
|
170
|
+
racking_model : string, optional
|
|
171
|
+
Valid strings are ``'open_rack'``, ``'close_mount'``,
|
|
172
|
+
``'insulated_back'``, ``'freestanding'`` and ``'insulated'``.
|
|
173
|
+
Used to identify a parameter set for the SAPM or PVsyst cell
|
|
174
|
+
temperature model.
|
|
175
|
+
See :py:func:`~pvlib.temperature.sapm_module` and
|
|
176
|
+
:py:func:`~pvlib.temperature.pvsyst_cell` for definitions.
|
|
176
177
|
|
|
177
178
|
losses_parameters : dict or Series, optional
|
|
178
179
|
Losses parameters as defined by PVWatts or other.
|
|
@@ -186,7 +187,7 @@ class PVSystem:
|
|
|
186
187
|
Raises
|
|
187
188
|
------
|
|
188
189
|
ValueError
|
|
189
|
-
If
|
|
190
|
+
If ``arrays`` is not None and has length 0.
|
|
190
191
|
|
|
191
192
|
See also
|
|
192
193
|
--------
|
|
@@ -312,7 +313,7 @@ class PVSystem:
|
|
|
312
313
|
dni_extra=None, airmass=None, albedo=None,
|
|
313
314
|
model='haydavies', **kwargs):
|
|
314
315
|
"""
|
|
315
|
-
Uses
|
|
316
|
+
Uses :py:func:`pvlib.irradiance.get_total_irradiance` to
|
|
316
317
|
calculate the plane of array irradiance components on the tilted
|
|
317
318
|
surfaces defined by each array's ``surface_tilt`` and
|
|
318
319
|
``surface_azimuth``.
|
|
@@ -323,11 +324,11 @@ class PVSystem:
|
|
|
323
324
|
Solar zenith angle.
|
|
324
325
|
solar_azimuth : float or Series
|
|
325
326
|
Solar azimuth angle.
|
|
326
|
-
dni : float
|
|
327
|
+
dni : float, Series, or tuple of float or Series
|
|
327
328
|
Direct Normal Irradiance. [W/m2]
|
|
328
|
-
ghi : float
|
|
329
|
+
ghi : float, Series, or tuple of float or Series
|
|
329
330
|
Global horizontal irradiance. [W/m2]
|
|
330
|
-
dhi : float
|
|
331
|
+
dhi : float, Series, or tuple of float or Series
|
|
331
332
|
Diffuse horizontal irradiance. [W/m2]
|
|
332
333
|
dni_extra : float, Series or tuple of float or Series, optional
|
|
333
334
|
Extraterrestrial direct normal irradiance. [W/m2]
|
|
@@ -339,15 +340,22 @@ class PVSystem:
|
|
|
339
340
|
Irradiance model.
|
|
340
341
|
|
|
341
342
|
kwargs
|
|
342
|
-
Extra parameters passed to
|
|
343
|
+
Extra parameters passed to
|
|
344
|
+
:py:func:`pvlib.irradiance.get_total_irradiance`.
|
|
343
345
|
|
|
344
346
|
Notes
|
|
345
347
|
-----
|
|
346
|
-
Each of
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
348
|
+
Each of ``dni``, ``ghi``, and ``dni`` may be passed as a float, Series,
|
|
349
|
+
or tuple of float or Series. If passed as a float or Series, these
|
|
350
|
+
values are used for all Arrays. If passed as a tuple, the tuple length
|
|
351
|
+
must be the same as the number of Arrays. The first tuple element is
|
|
352
|
+
used for the first Array, the second tuple element for the second
|
|
353
|
+
Array, and so forth.
|
|
354
|
+
|
|
355
|
+
Some sky irradiance models require ``dni_extra``. For these models,
|
|
356
|
+
if ``dni_extra`` is not provided and ``solar_zenith`` has a
|
|
357
|
+
``DatetimeIndex``, then ``dni_extra`` is calculated.
|
|
358
|
+
Otherwise, ``dni_extra=1367`` is assumed.
|
|
351
359
|
|
|
352
360
|
Returns
|
|
353
361
|
-------
|
|
@@ -1077,7 +1085,7 @@ class Array:
|
|
|
1077
1085
|
"""
|
|
1078
1086
|
Get plane of array irradiance components.
|
|
1079
1087
|
|
|
1080
|
-
Uses
|
|
1088
|
+
Uses :py:func:`pvlib.irradiance.get_total_irradiance` to
|
|
1081
1089
|
calculate the plane of array irradiance components for a surface
|
|
1082
1090
|
defined by ``self.surface_tilt`` and ``self.surface_azimuth``.
|
|
1083
1091
|
|
|
@@ -1112,6 +1120,13 @@ class Array:
|
|
|
1112
1120
|
Column names are: ``'poa_global', 'poa_direct', 'poa_diffuse',
|
|
1113
1121
|
'poa_sky_diffuse', 'poa_ground_diffuse'``.
|
|
1114
1122
|
|
|
1123
|
+
Notes
|
|
1124
|
+
-----
|
|
1125
|
+
Some sky irradiance models require ``dni_extra``. For these models,
|
|
1126
|
+
if ``dni_extra`` is not provided and ``solar_zenith`` has a
|
|
1127
|
+
``DatetimeIndex``, then ``dni_extra`` is calculated.
|
|
1128
|
+
Otherwise, ``dni_extra=1367`` is assumed.
|
|
1129
|
+
|
|
1115
1130
|
See also
|
|
1116
1131
|
--------
|
|
1117
1132
|
:py:func:`pvlib.irradiance.get_total_irradiance`
|
|
@@ -1119,9 +1134,16 @@ class Array:
|
|
|
1119
1134
|
if albedo is None:
|
|
1120
1135
|
albedo = self.albedo
|
|
1121
1136
|
|
|
1122
|
-
# not needed for all models, but this is easier
|
|
1137
|
+
# dni_extra is not needed for all models, but this is easier
|
|
1123
1138
|
if dni_extra is None:
|
|
1124
|
-
|
|
1139
|
+
if (hasattr(solar_zenith, 'index') and
|
|
1140
|
+
isinstance(solar_zenith.index, pd.DatetimeIndex)):
|
|
1141
|
+
# calculate extraterrestrial irradiance
|
|
1142
|
+
dni_extra = irradiance.get_extra_radiation(
|
|
1143
|
+
solar_zenith.index)
|
|
1144
|
+
else:
|
|
1145
|
+
# use the solar constant
|
|
1146
|
+
dni_extra = 1367.0
|
|
1125
1147
|
|
|
1126
1148
|
if airmass is None:
|
|
1127
1149
|
airmass = atmosphere.get_relative_airmass(solar_zenith)
|
|
@@ -1374,8 +1396,12 @@ class FixedMount(AbstractMount):
|
|
|
1374
1396
|
West=270. [degrees]
|
|
1375
1397
|
|
|
1376
1398
|
racking_model : str, optional
|
|
1377
|
-
Valid strings are 'open_rack'
|
|
1378
|
-
|
|
1399
|
+
Valid strings are ``'open_rack'``, ``'close_mount'``,
|
|
1400
|
+
``'insulated_back'``, ``'freestanding'`` and ``'insulated'``.
|
|
1401
|
+
Used to identify a parameter set for the SAPM or PVsyst cell
|
|
1402
|
+
temperature model.
|
|
1403
|
+
See :py:func:`~pvlib.temperature.sapm_module` and
|
|
1404
|
+
:py:func:`~pvlib.temperature.pvsyst_cell` for definitions.
|
|
1379
1405
|
|
|
1380
1406
|
module_height : float, optional
|
|
1381
1407
|
The height above ground of the center of the module [m]. Used for
|
|
@@ -1451,8 +1477,13 @@ class SingleAxisTrackerMount(AbstractMount):
|
|
|
1451
1477
|
`cross_axis_tilt`. [degrees]
|
|
1452
1478
|
|
|
1453
1479
|
racking_model : str, optional
|
|
1454
|
-
Valid strings are 'open_rack'
|
|
1455
|
-
|
|
1480
|
+
Valid strings are ``'open_rack'``, ``'close_mount'``,
|
|
1481
|
+
``'insulated_back'``, ``'freestanding'`` and ``'insulated'``.
|
|
1482
|
+
Used to identify a parameter set for the SAPM or PVsyst cell
|
|
1483
|
+
temperature model. ``'open_rack'`` or ``'freestanding'`` should
|
|
1484
|
+
be used for systems with single-axis trackers.
|
|
1485
|
+
See :py:func:`~pvlib.temperature.sapm_module` and
|
|
1486
|
+
:py:func:`~pvlib.temperature.pvsyst_cell` for definitions.
|
|
1456
1487
|
|
|
1457
1488
|
module_height : float, optional
|
|
1458
1489
|
The height above ground of the center of the module [m]. Used for
|
|
@@ -1965,10 +1996,10 @@ def retrieve_sam(name=None, path=None):
|
|
|
1965
1996
|
|
|
1966
1997
|
This function will retrieve either:
|
|
1967
1998
|
|
|
1968
|
-
|
|
1969
|
-
|
|
1970
|
-
|
|
1971
|
-
|
|
1999
|
+
* CEC module database
|
|
2000
|
+
* Sandia Module database
|
|
2001
|
+
* CEC Inverter database
|
|
2002
|
+
* Anton Driesse Inverter database
|
|
1972
2003
|
|
|
1973
2004
|
and return it as a pandas DataFrame.
|
|
1974
2005
|
|
|
@@ -1981,20 +2012,20 @@ def retrieve_sam(name=None, path=None):
|
|
|
1981
2012
|
Use one of the following strings to retrieve a database bundled with
|
|
1982
2013
|
pvlib:
|
|
1983
2014
|
|
|
1984
|
-
* 'CECMod' - returns the CEC module database
|
|
1985
|
-
* 'CECInverter' - returns the CEC Inverter database
|
|
1986
|
-
* 'SandiaInverter' - returns the CEC Inverter database
|
|
2015
|
+
* ``'CECMod'`` - returns the CEC module database
|
|
2016
|
+
* ``'CECInverter'`` - returns the CEC Inverter database
|
|
2017
|
+
* ``'SandiaInverter'`` - returns the CEC Inverter database
|
|
1987
2018
|
(CEC is only current inverter db available; tag kept for
|
|
1988
2019
|
backwards compatibility)
|
|
1989
|
-
* 'SandiaMod' - returns the Sandia Module database
|
|
1990
|
-
* 'ADRInverter' - returns the ADR Inverter database
|
|
2020
|
+
* ``'SandiaMod'`` - returns the Sandia Module database
|
|
2021
|
+
* ``'ADRInverter'`` - returns the ADR Inverter database
|
|
1991
2022
|
|
|
1992
2023
|
path : string, optional
|
|
1993
2024
|
Path to a CSV file or a URL.
|
|
1994
2025
|
|
|
1995
2026
|
Returns
|
|
1996
2027
|
-------
|
|
1997
|
-
|
|
2028
|
+
DataFrame
|
|
1998
2029
|
A DataFrame containing all the elements of the desired database.
|
|
1999
2030
|
Each column represents a module or inverter, and a specific
|
|
2000
2031
|
dataset can be retrieved by the command
|
|
@@ -2012,14 +2043,13 @@ def retrieve_sam(name=None, path=None):
|
|
|
2012
2043
|
-----
|
|
2013
2044
|
Files available at
|
|
2014
2045
|
https://github.com/NREL/SAM/tree/develop/deploy/libraries
|
|
2015
|
-
Documentation for module and inverter data sets:
|
|
2016
|
-
https://sam.nrel.gov/photovoltaic/pv-sub-page-2.html
|
|
2017
2046
|
|
|
2018
2047
|
Examples
|
|
2019
2048
|
--------
|
|
2049
|
+
Using a database bundled with pvlib:
|
|
2020
2050
|
|
|
2021
2051
|
>>> from pvlib import pvsystem
|
|
2022
|
-
>>> invdb = pvsystem.retrieve_sam('CECInverter')
|
|
2052
|
+
>>> invdb = pvsystem.retrieve_sam(name='CECInverter')
|
|
2023
2053
|
>>> inverter = invdb.AE_Solar_Energy__AE6_0__277V_
|
|
2024
2054
|
>>> inverter
|
|
2025
2055
|
Vac 277
|
|
@@ -2039,7 +2069,15 @@ def retrieve_sam(name=None, path=None):
|
|
|
2039
2069
|
CEC_Date NaN
|
|
2040
2070
|
CEC_Type Utility Interactive
|
|
2041
2071
|
Name: AE_Solar_Energy__AE6_0__277V_, dtype: object
|
|
2042
|
-
|
|
2072
|
+
|
|
2073
|
+
Using a remote database, via URL:
|
|
2074
|
+
|
|
2075
|
+
>>> url = "https://raw.githubusercontent.com/NREL/SAM/refs/heads/develop/deploy/libraries/CEC%20Inverters.csv"
|
|
2076
|
+
>>> inv_db = pvsystem.retrieve_sam(path=url)
|
|
2077
|
+
>>> inv_db.keys()
|
|
2078
|
+
Index(['ABB__PVI_3_0_OUTD_S_US_A__208V_', 'ABB__PVI_3_0_OUTD_S_US_A__240V_', ...],
|
|
2079
|
+
dtype='object', length=...)
|
|
2080
|
+
""" # noqa: E501
|
|
2043
2081
|
# error: path was previously silently ignored if name was given GH#2018
|
|
2044
2082
|
if name is not None and path is not None:
|
|
2045
2083
|
raise ValueError("Please provide either 'name' or 'path', not both.")
|
|
@@ -2871,46 +2909,49 @@ def pvwatts_losses(soiling=2, shading=3, snow=0, mismatch=2, wiring=2,
|
|
|
2871
2909
|
def dc_ohms_from_percent(vmp_ref, imp_ref, dc_ohmic_percent,
|
|
2872
2910
|
modules_per_string=1,
|
|
2873
2911
|
strings=1):
|
|
2874
|
-
"""
|
|
2875
|
-
|
|
2876
|
-
ohmic loss at
|
|
2877
|
-
|
|
2878
|
-
Equivalent resistance is calculated with the function:
|
|
2879
|
-
|
|
2880
|
-
.. math::
|
|
2881
|
-
Rw = (L_{stc} / 100) * (Varray / Iarray)
|
|
2882
|
-
|
|
2883
|
-
:math:`Rw` is the equivalent resistance in ohms
|
|
2884
|
-
:math:`Varray` is the Vmp of the modules times modules per string
|
|
2885
|
-
:math:`Iarray` is the Imp of the modules times strings per array
|
|
2886
|
-
:math:`L_{stc}` is the input dc loss percent
|
|
2912
|
+
r"""
|
|
2913
|
+
Calculate the equivalent resistance of the conductors from the percent
|
|
2914
|
+
ohmic loss of an array at reference conditions.
|
|
2887
2915
|
|
|
2888
2916
|
Parameters
|
|
2889
2917
|
----------
|
|
2890
2918
|
vmp_ref: numeric
|
|
2891
|
-
|
|
2919
|
+
Maximum power voltage of one module at reference conditions. [V]
|
|
2892
2920
|
imp_ref: numeric
|
|
2893
|
-
|
|
2894
|
-
dc_ohmic_percent: numeric
|
|
2895
|
-
|
|
2921
|
+
Maximum power current of one module at reference conditions. [A]
|
|
2922
|
+
dc_ohmic_percent: numeric
|
|
2923
|
+
Array DC power loss as a percent of DC power loss at reference
|
|
2924
|
+
conditions. In percent, e.g. 1.5% loss is input as 1.5.
|
|
2896
2925
|
modules_per_string: int, default 1
|
|
2897
|
-
Number of modules per string in the array.
|
|
2926
|
+
Number of series-connected modules per string in the array.
|
|
2898
2927
|
strings: int, default 1
|
|
2899
2928
|
Number of parallel strings in the array.
|
|
2900
2929
|
|
|
2901
2930
|
Returns
|
|
2902
2931
|
----------
|
|
2903
2932
|
Rw: numeric
|
|
2904
|
-
Equivalent resistance [ohm]
|
|
2933
|
+
Equivalent resistance. [ohm]
|
|
2905
2934
|
|
|
2906
2935
|
See Also
|
|
2907
2936
|
--------
|
|
2908
2937
|
pvlib.pvsystem.dc_ohmic_losses
|
|
2909
2938
|
|
|
2910
|
-
|
|
2911
|
-
|
|
2912
|
-
|
|
2913
|
-
|
|
2939
|
+
Notes
|
|
2940
|
+
-----
|
|
2941
|
+
Equivalent resistance is calculated as:
|
|
2942
|
+
|
|
2943
|
+
.. math::
|
|
2944
|
+
|
|
2945
|
+
R_w = \left(\frac{L_{stc}}{100}\right) \times \left(\frac{
|
|
2946
|
+
V_{array}}{I_{array}}\right)
|
|
2947
|
+
|
|
2948
|
+
:math:`R_w` is the equivalent resistance in ohms.
|
|
2949
|
+
:math:`V_{array}` is the array voltage, equal to ``vmp_ref`` times
|
|
2950
|
+
``modules_per_string``.
|
|
2951
|
+
:math:`I_{array}` is the array current, equal to ``imp_ref`` times
|
|
2952
|
+
``strings``.
|
|
2953
|
+
:math:`L_{stc}` is the input DC loss percent at reference conditions.
|
|
2954
|
+
|
|
2914
2955
|
"""
|
|
2915
2956
|
vmp = modules_per_string * vmp_ref
|
|
2916
2957
|
|
|
@@ -2922,30 +2963,37 @@ def dc_ohms_from_percent(vmp_ref, imp_ref, dc_ohmic_percent,
|
|
|
2922
2963
|
|
|
2923
2964
|
|
|
2924
2965
|
def dc_ohmic_losses(resistance, current):
|
|
2925
|
-
"""
|
|
2966
|
+
r"""
|
|
2926
2967
|
Returns ohmic losses in units of power from the equivalent
|
|
2927
2968
|
resistance of the wires and the operating current.
|
|
2928
2969
|
|
|
2929
2970
|
Parameters
|
|
2930
2971
|
----------
|
|
2931
2972
|
resistance: numeric
|
|
2932
|
-
Equivalent resistance of wires [ohm]
|
|
2973
|
+
Equivalent resistance of wires. [ohm]
|
|
2933
2974
|
current: numeric, float or array-like
|
|
2934
|
-
Operating current [A]
|
|
2975
|
+
Operating current. [A]
|
|
2935
2976
|
|
|
2936
2977
|
Returns
|
|
2937
2978
|
----------
|
|
2938
2979
|
loss: numeric
|
|
2939
|
-
Power
|
|
2980
|
+
Power loss. [W]
|
|
2940
2981
|
|
|
2941
2982
|
See Also
|
|
2942
2983
|
--------
|
|
2943
2984
|
pvlib.pvsystem.dc_ohms_from_percent
|
|
2944
2985
|
|
|
2945
|
-
|
|
2946
|
-
|
|
2947
|
-
|
|
2948
|
-
|
|
2986
|
+
Notes
|
|
2987
|
+
-----
|
|
2988
|
+
Ohmic (also termed joule or heat) loss is the power lost due to current
|
|
2989
|
+
flowing through a conductor. Ohmic loss, :math:`L`, is computed as
|
|
2990
|
+
|
|
2991
|
+
.. math::
|
|
2992
|
+
|
|
2993
|
+
L = I^2 \times R
|
|
2994
|
+
|
|
2995
|
+
where :math:`I` is the current (A) and :math:`R` is the resistance of the
|
|
2996
|
+
conductor (ohms).
|
|
2949
2997
|
"""
|
|
2950
2998
|
return resistance * current * current
|
|
2951
2999
|
|
pvlib/solarposition.py
CHANGED
|
@@ -30,7 +30,7 @@ from pvlib.tools import datetime_to_djd, djd_to_datetime
|
|
|
30
30
|
def get_solarposition(time, latitude, longitude,
|
|
31
31
|
altitude=None, pressure=None,
|
|
32
32
|
method='nrel_numpy',
|
|
33
|
-
temperature=12, **kwargs):
|
|
33
|
+
temperature=12.0, **kwargs):
|
|
34
34
|
"""
|
|
35
35
|
A convenience wrapper for the solar position calculators.
|
|
36
36
|
|
|
@@ -125,8 +125,8 @@ def get_solarposition(time, latitude, longitude,
|
|
|
125
125
|
return ephem_df
|
|
126
126
|
|
|
127
127
|
|
|
128
|
-
def spa_c(time, latitude, longitude, pressure=101325
|
|
129
|
-
temperature=12
|
|
128
|
+
def spa_c(time, latitude, longitude, pressure=101325., altitude=0.,
|
|
129
|
+
temperature=12., delta_t=67.0,
|
|
130
130
|
raw_spa_output=False):
|
|
131
131
|
r"""
|
|
132
132
|
Calculate the solar position using the C implementation of the NREL
|
|
@@ -149,11 +149,11 @@ def spa_c(time, latitude, longitude, pressure=101325, altitude=0,
|
|
|
149
149
|
longitude : float
|
|
150
150
|
Longitude in decimal degrees. Positive east of prime meridian,
|
|
151
151
|
negative to west.
|
|
152
|
-
pressure : float, default 101325
|
|
152
|
+
pressure : float, default 101325.0
|
|
153
153
|
Pressure in Pascals
|
|
154
|
-
altitude : float, default 0
|
|
154
|
+
altitude : float, default 0.0
|
|
155
155
|
Height above sea level. [m]
|
|
156
|
-
temperature : float, default 12
|
|
156
|
+
temperature : float, default 12.0
|
|
157
157
|
Temperature in C
|
|
158
158
|
delta_t : float, default 67.0
|
|
159
159
|
Difference between terrestrial time and UT1.
|
|
@@ -279,7 +279,7 @@ def _datetime_to_unixtime(dtindex):
|
|
|
279
279
|
|
|
280
280
|
|
|
281
281
|
def spa_python(time, latitude, longitude,
|
|
282
|
-
altitude=0
|
|
282
|
+
altitude=0., pressure=101325., temperature=12., delta_t=67.0,
|
|
283
283
|
atmos_refract=None, how='numpy', numthreads=4):
|
|
284
284
|
"""
|
|
285
285
|
Calculate the solar position using a python implementation of the
|
|
@@ -302,11 +302,11 @@ def spa_python(time, latitude, longitude,
|
|
|
302
302
|
longitude : float
|
|
303
303
|
Longitude in decimal degrees. Positive east of prime meridian,
|
|
304
304
|
negative to west.
|
|
305
|
-
altitude : float, default 0
|
|
305
|
+
altitude : float, default 0.0
|
|
306
306
|
Distance above sea level.
|
|
307
|
-
pressure : int or float, optional, default 101325
|
|
307
|
+
pressure : int or float, optional, default 101325.0
|
|
308
308
|
avg. yearly air pressure in Pascals.
|
|
309
|
-
temperature : int or float, optional, default 12
|
|
309
|
+
temperature : int or float, optional, default 12.0
|
|
310
310
|
avg. yearly air temperature in degrees C.
|
|
311
311
|
delta_t : float or array, optional, default 67.0
|
|
312
312
|
Difference between terrestrial time and UT1.
|
|
@@ -507,9 +507,9 @@ def _ephem_setup(latitude, longitude, altitude, pressure, temperature,
|
|
|
507
507
|
|
|
508
508
|
def sun_rise_set_transit_ephem(times, latitude, longitude,
|
|
509
509
|
next_or_previous='next',
|
|
510
|
-
altitude=0
|
|
511
|
-
pressure=101325
|
|
512
|
-
temperature=12
|
|
510
|
+
altitude=0.,
|
|
511
|
+
pressure=101325.,
|
|
512
|
+
temperature=12., horizon='0:00'):
|
|
513
513
|
"""
|
|
514
514
|
Calculate the next sunrise and sunset times using the PyEphem package.
|
|
515
515
|
|
|
@@ -523,11 +523,11 @@ def sun_rise_set_transit_ephem(times, latitude, longitude,
|
|
|
523
523
|
Longitude in degrees, positive east of prime meridian, negative to west
|
|
524
524
|
next_or_previous : str
|
|
525
525
|
'next' or 'previous' sunrise and sunset relative to time
|
|
526
|
-
altitude : float, default 0
|
|
526
|
+
altitude : float, default 0.0
|
|
527
527
|
distance above sea level in meters.
|
|
528
|
-
pressure : int or float, optional, default 101325
|
|
528
|
+
pressure : int or float, optional, default 101325.0
|
|
529
529
|
air pressure in Pascals.
|
|
530
|
-
temperature : int or float, optional, default 12
|
|
530
|
+
temperature : int or float, optional, default 12.0
|
|
531
531
|
air temperature in degrees C.
|
|
532
532
|
horizon : string, format +/-X:YY
|
|
533
533
|
arc degrees:arc minutes from geometrical horizon for sunrise and
|
|
@@ -590,8 +590,8 @@ def sun_rise_set_transit_ephem(times, latitude, longitude,
|
|
|
590
590
|
'transit': trans})
|
|
591
591
|
|
|
592
592
|
|
|
593
|
-
def pyephem(time, latitude, longitude, altitude=0
|
|
594
|
-
temperature=12
|
|
593
|
+
def pyephem(time, latitude, longitude, altitude=0., pressure=101325.,
|
|
594
|
+
temperature=12., horizon='+0:00'):
|
|
595
595
|
"""
|
|
596
596
|
Calculate the solar position using the PyEphem package.
|
|
597
597
|
|
|
@@ -605,11 +605,11 @@ def pyephem(time, latitude, longitude, altitude=0, pressure=101325,
|
|
|
605
605
|
longitude : float
|
|
606
606
|
Longitude in decimal degrees. Positive east of prime meridian,
|
|
607
607
|
negative to west.
|
|
608
|
-
altitude : float, default 0
|
|
608
|
+
altitude : float, default 0.0
|
|
609
609
|
Height above sea level in meters. [m]
|
|
610
|
-
pressure : int or float, optional, default 101325
|
|
610
|
+
pressure : int or float, optional, default 101325.0
|
|
611
611
|
air pressure in Pascals.
|
|
612
|
-
temperature : int or float, optional, default 12
|
|
612
|
+
temperature : int or float, optional, default 12.0
|
|
613
613
|
air temperature in degrees C.
|
|
614
614
|
horizon : string, optional, default '+0:00'
|
|
615
615
|
arc degrees:arc minutes from geometrical horizon for sunrise and
|
|
@@ -679,7 +679,7 @@ def pyephem(time, latitude, longitude, altitude=0, pressure=101325,
|
|
|
679
679
|
return sun_coords
|
|
680
680
|
|
|
681
681
|
|
|
682
|
-
def ephemeris(time, latitude, longitude, pressure=101325, temperature=12):
|
|
682
|
+
def ephemeris(time, latitude, longitude, pressure=101325.0, temperature=12.0):
|
|
683
683
|
"""
|
|
684
684
|
Python-native solar position calculator.
|
|
685
685
|
The accuracy of this code is not guaranteed.
|
|
@@ -695,9 +695,9 @@ def ephemeris(time, latitude, longitude, pressure=101325, temperature=12):
|
|
|
695
695
|
longitude : float
|
|
696
696
|
Longitude in decimal degrees. Positive east of prime meridian,
|
|
697
697
|
negative to west.
|
|
698
|
-
pressure : float or Series, default 101325
|
|
698
|
+
pressure : float or Series, default 101325.0
|
|
699
699
|
Ambient pressure (Pascals)
|
|
700
|
-
temperature : float or Series, default 12
|
|
700
|
+
temperature : float or Series, default 12.0
|
|
701
701
|
Ambient temperature (C)
|
|
702
702
|
|
|
703
703
|
Returns
|
|
@@ -856,8 +856,8 @@ def ephemeris(time, latitude, longitude, pressure=101325, temperature=12):
|
|
|
856
856
|
|
|
857
857
|
|
|
858
858
|
def calc_time(lower_bound, upper_bound, latitude, longitude, attribute, value,
|
|
859
|
-
altitude=0, pressure=101325, temperature=12
|
|
860
|
-
xtol=1.0e-12):
|
|
859
|
+
altitude=0.0, pressure=101325.0, temperature=12.0,
|
|
860
|
+
horizon='+0:00', xtol=1.0e-12):
|
|
861
861
|
"""
|
|
862
862
|
Calculate the time between lower_bound and upper_bound
|
|
863
863
|
where the attribute is equal to value. Uses PyEphem for
|
|
@@ -879,12 +879,12 @@ def calc_time(lower_bound, upper_bound, latitude, longitude, attribute, value,
|
|
|
879
879
|
and 'az' (which must be given in radians).
|
|
880
880
|
value : int or float
|
|
881
881
|
The value of the attribute to solve for
|
|
882
|
-
altitude : float, default 0
|
|
882
|
+
altitude : float, default 0.0
|
|
883
883
|
Distance above sea level.
|
|
884
|
-
pressure : int or float, optional, default 101325
|
|
884
|
+
pressure : int or float, optional, default 101325.0
|
|
885
885
|
Air pressure in Pascals. Set to 0 for no
|
|
886
886
|
atmospheric correction.
|
|
887
|
-
temperature : int or float, optional, default 12
|
|
887
|
+
temperature : int or float, optional, default 12.0
|
|
888
888
|
Air temperature in degrees C.
|
|
889
889
|
horizon : string, optional, default '+0:00'
|
|
890
890
|
arc degrees:arc minutes from geometrical horizon for sunrise and
|
|
@@ -1349,6 +1349,12 @@ def hour_angle(times, longitude, equation_of_time):
|
|
|
1349
1349
|
times : :class:`pandas.DatetimeIndex`
|
|
1350
1350
|
Corresponding timestamps, must be localized to the timezone for the
|
|
1351
1351
|
``longitude``.
|
|
1352
|
+
|
|
1353
|
+
A `pytz.exceptions.AmbiguousTimeError` will be raised if any of the
|
|
1354
|
+
given times are on a day when the local daylight savings transition
|
|
1355
|
+
happens at midnight. If you're working with such a timezone,
|
|
1356
|
+
consider converting to a non-DST timezone (e.g. GMT-4) before
|
|
1357
|
+
calling this function.
|
|
1352
1358
|
longitude : numeric
|
|
1353
1359
|
Longitude in degrees
|
|
1354
1360
|
equation_of_time : numeric
|
|
@@ -1421,7 +1427,17 @@ def _times_to_hours_after_local_midnight(times):
|
|
|
1421
1427
|
if not times.tz:
|
|
1422
1428
|
raise ValueError('times must be localized')
|
|
1423
1429
|
|
|
1424
|
-
|
|
1430
|
+
# Some timezones have a DST shift at midnight:
|
|
1431
|
+
# 11:59pm -> 1:00am - results in a nonexistent midnight
|
|
1432
|
+
# 12:59am -> 12:00am - results in an ambiguous midnight
|
|
1433
|
+
# We remove the timezone before normalizing for this reason.
|
|
1434
|
+
naive_normalized_times = times.tz_localize(None).normalize()
|
|
1435
|
+
|
|
1436
|
+
# Use Pandas functionality for shifting nonexistent times forward
|
|
1437
|
+
normalized_times = naive_normalized_times.tz_localize(
|
|
1438
|
+
times.tz, nonexistent='shift_forward', ambiguous='raise')
|
|
1439
|
+
|
|
1440
|
+
hrs = (times - normalized_times) / pd.Timedelta('1h')
|
|
1425
1441
|
|
|
1426
1442
|
# ensure array return instead of a version-dependent pandas <T>Index
|
|
1427
1443
|
return np.array(hrs)
|
pvlib/spa.py
CHANGED
|
@@ -413,8 +413,10 @@ def julian_day_dt(year, month, day, hour, minute, second, microsecond):
|
|
|
413
413
|
frac_of_day = (microsecond / 1e6 + (second + minute * 60 + hour * 3600)
|
|
414
414
|
) * 1.0 / (3600*24)
|
|
415
415
|
d = day + frac_of_day
|
|
416
|
-
jd =
|
|
417
|
-
|
|
416
|
+
jd = int(365.25 * (year + 4716)) + int(30.6001 * (month + 1)) + d - 1524.5
|
|
417
|
+
if jd > 2299160.0:
|
|
418
|
+
jd += b
|
|
419
|
+
|
|
418
420
|
return jd
|
|
419
421
|
|
|
420
422
|
|
pvlib/spectrum/irradiance.py
CHANGED
|
@@ -189,7 +189,8 @@ def average_photon_energy(spectra):
|
|
|
189
189
|
----------
|
|
190
190
|
spectra : pandas.Series or pandas.DataFrame
|
|
191
191
|
|
|
192
|
-
Spectral irradiance, must be positive
|
|
192
|
+
Spectral irradiance, must be positive [Wm⁻²nm⁻¹].
|
|
193
|
+
See :term:`spectra`.
|
|
193
194
|
|
|
194
195
|
A single spectrum must be a :py:class:`pandas.Series` with wavelength
|
|
195
196
|
[nm] as the index, while multiple spectra must be rows in a
|
pvlib/spectrum/spectrl2.py
CHANGED
|
@@ -228,10 +228,11 @@ def spectrl2(apparent_zenith, aoi, surface_tilt, ground_albedo,
|
|
|
228
228
|
Returns
|
|
229
229
|
-------
|
|
230
230
|
spectra_components : dict
|
|
231
|
-
A dict of arrays.
|
|
231
|
+
A dict of arrays. With the exception of `wavelength`, which has length
|
|
232
232
|
122, each array has shape (122, N) where N is the length of the
|
|
233
233
|
input ``apparent_zenith``. All values are spectral irradiance
|
|
234
234
|
with units Wm⁻²nm⁻¹, except for `wavelength`, which is in nanometers.
|
|
235
|
+
See :term:`spectra_components`.
|
|
235
236
|
|
|
236
237
|
* wavelength
|
|
237
238
|
* dni_extra
|