NREL-reV 0.9.2__py3-none-any.whl → 0.9.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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: NREL-reV
3
- Version: 0.9.2
3
+ Version: 0.9.5
4
4
  Summary: National Renewable Energy Laboratory's (NREL's) Renewable Energy Potential(V) Model: reV
5
5
  Home-page: https://nrel.github.io/reV/
6
6
  Author: Galen Maclaurin
@@ -17,22 +17,22 @@ Classifier: Programming Language :: Python :: 3.9
17
17
  Classifier: Programming Language :: Python :: 3.10
18
18
  Classifier: Programming Language :: Python :: 3.11
19
19
  Requires-Python: >=3.8
20
- Requires-Dist: NREL-gaps >=0.6.11
21
- Requires-Dist: NREL-NRWAL >=0.0.7
22
- Requires-Dist: NREL-PySAM ~=4.1.0
23
- Requires-Dist: NREL-rex >=0.2.85
24
- Requires-Dist: numpy ~=1.24.4
25
- Requires-Dist: packaging >=20.3
26
- Requires-Dist: plotly >=4.7.1
27
- Requires-Dist: plotting >=0.0.6
20
+ Requires-Dist: NREL-gaps>=0.6.11
21
+ Requires-Dist: NREL-NRWAL>=0.0.7
22
+ Requires-Dist: NREL-PySAM~=4.1.0
23
+ Requires-Dist: NREL-rex>=0.2.89
24
+ Requires-Dist: numpy~=1.24.4
25
+ Requires-Dist: packaging>=20.3
26
+ Requires-Dist: plotly>=4.7.1
27
+ Requires-Dist: plotting>=0.0.6
28
28
  Requires-Dist: shapely
29
29
  Provides-Extra: dev
30
- Requires-Dist: pytest >=5.2 ; extra == 'dev'
31
- Requires-Dist: flake8 ; extra == 'dev'
32
- Requires-Dist: pre-commit ; extra == 'dev'
33
- Requires-Dist: pylint ; extra == 'dev'
30
+ Requires-Dist: pytest>=5.2; extra == "dev"
31
+ Requires-Dist: flake8; extra == "dev"
32
+ Requires-Dist: pre-commit; extra == "dev"
33
+ Requires-Dist: pylint; extra == "dev"
34
34
  Provides-Extra: test
35
- Requires-Dist: pytest >=5.2 ; extra == 'test'
35
+ Requires-Dist: pytest>=5.2; extra == "test"
36
36
 
37
37
 
38
38
                 
@@ -1,11 +1,11 @@
1
1
  reV/__init__.py,sha256=tXTpWu_qVo3uotfSw_TJ-gNbidGaIPPfUTwBlpCMJ-g,856
2
2
  reV/cli.py,sha256=jfGGOr6QlLz8ghA7vBgx5-VgNsy4bBQo5DdHk42-q9A,1601
3
- reV/version.py,sha256=ZggWF5z5HY0xtKYNitKGKEQSDJ5G21AZQKZMzs5u-wo,50
4
- reV/SAM/SAM.py,sha256=SUyaWK3InUh90iQqbka-g_X36EfGuwslEfKEPCIpMrw,31691
3
+ reV/version.py,sha256=-d0FHT8TbXm_fBuvfSz3da_dWANi_ww6eK4n0DOIYU0,50
4
+ reV/SAM/SAM.py,sha256=1xuxs2gb1wsgbBkhj3mdQVDuSWbp5T5Bh7kLRl69pkg,32258
5
5
  reV/SAM/__init__.py,sha256=LJqoncyKDY5ZP5WA4kboh561bce11F9Ge645Izah0EY,240
6
6
  reV/SAM/defaults.py,sha256=2zqT_mfrVtbvU7Pe6H4anNtiVkIyQbuJcGIOARzEsbM,7193
7
7
  reV/SAM/econ.py,sha256=dFhtUXp5eozSsPyk0XXji0HGexKJnxoct8cwE1ApHVg,20704
8
- reV/SAM/generation.py,sha256=D4vkir6uU9QgY_9AMQOXA-4blGcQoxRH0O6PEfgqWok,89142
8
+ reV/SAM/generation.py,sha256=vUM2DUHCsKh_FBzuUKtFsq_oUXxm47c-oP33KvfA7Ow,86524
9
9
  reV/SAM/version_checker.py,sha256=q-eXsmSB08A5hSelNH7uAe_bqPpqjsxaiS3OBjXBs-0,3997
10
10
  reV/SAM/windbos.py,sha256=fnq1uxtSl-vtJth0gTlHkCSsmvDbRROCo9RGdqA7hK4,7504
11
11
  reV/SAM/defaults/USA AZ Phoenix Sky Harbor Intl Ap (TMY3).csv,sha256=8QorTX0ACjgPgNV7kLSpTHOqfY4E17gkkpKB-qseiFk,406896
@@ -14,7 +14,7 @@ reV/SAM/defaults/US_Wave.csv,sha256=wvn9vGl9ZGKVHbCyq4muhMI6x1-nAaQfDS3hC4ftwBA,
14
14
  reV/SAM/defaults/geothermal.json,sha256=ivxnpxkfBrEl1MwLKXClLJfTfvF5UrbN87wpC_BFLck,2598
15
15
  reV/SAM/defaults/i_pvwattsv5.json,sha256=pZpNlK5MiowZmNwY7i9XRWp9G8pPLirwdBWCMVJVuKE,312
16
16
  reV/bespoke/__init__.py,sha256=vpXbyBUrUsTgK8UP_LafMjLiDg2CRG9WZLHPsOJoxek,109
17
- reV/bespoke/bespoke.py,sha256=DgNPIeCmeqpOSaMbaqmJKQGatoLd8MOPTTQpZBlvzJI,110353
17
+ reV/bespoke/bespoke.py,sha256=nWmryaLRFkOwkYLkKUQHgjXqc5YcFGODK4k6VEX0bRU,113473
18
18
  reV/bespoke/cli_bespoke.py,sha256=nZc6rJlfxH2IXUz9bym4EO-C1k6VvulgweWoRrMg_cE,3028
19
19
  reV/bespoke/gradient_free.py,sha256=URWV1yiO2jyWk3_GOpfpLV_wlgJhXXGmTUwCB3WTV0Y,12015
20
20
  reV/bespoke/pack_turbs.py,sha256=l4btC2dPZkLvDgAAGVhAYgAZDbvwimGYRdrQDq0xT68,3740
@@ -37,7 +37,7 @@ reV/econ/utilities.py,sha256=ZOA49S1jfsvdenvlL7m-BAJIrAvpAHSix5-wrSW0uLc,1232
37
37
  reV/generation/__init__.py,sha256=LBecrbpL69tROol_OwVHTKBrTqgSSxJW59fs0k3o0jQ,75
38
38
  reV/generation/base.py,sha256=p6g8Bj8T98OfKu44LTocGtEozstbUvti6wSi3oroS5U,48758
39
39
  reV/generation/cli_gen.py,sha256=5RSlr8yO9zlB-1FzFZGClqsxqsrbr9rcS_8PlOjVx2s,4435
40
- reV/generation/generation.py,sha256=jtlUcfmQKDcXarRwj-iJBS_60TG-w2TKoowfU_1tBQg,46981
40
+ reV/generation/generation.py,sha256=o6nJlEcgs-QQ_fdqva-7jOhWl1wj-J7CIrRR5qNJyEQ,47434
41
41
  reV/generation/output_attributes/generation.json,sha256=cy8efVCJgNSYCsR3x3_VpMCtynYS3oaQG4M2MwcdzFY,4954
42
42
  reV/generation/output_attributes/lcoe_fcr.json,sha256=d_TGMkZsmsfDXQiWfhYjFkmwqi-wKF8JdHmiMCj2h38,136
43
43
  reV/generation/output_attributes/lcoe_fcr_inputs.json,sha256=Yb-WTXt9YD4wE4Uu315W2uLFH6g3fT40YY83mxS-aWE,1289
@@ -51,7 +51,7 @@ reV/handlers/__init__.py,sha256=N7KfWbXfHLizMpoUw6yo0egbyq3jb9QL4YouBLUf4mI,130
51
51
  reV/handlers/cli_collect.py,sha256=QRjhuJ1lV4BwGoguu0m4etrNRPMXGIZlijNyYsb7_5U,799
52
52
  reV/handlers/cli_multi_year.py,sha256=xMAQ70lVUMAPM10EkZwc_FreQLjnzQ9VmKl48MS1SO0,660
53
53
  reV/handlers/exclusions.py,sha256=_s-LHbjHAAHSIM6tFXCoJlLKcv0FBxbm6JAmuE_X_-I,12266
54
- reV/handlers/multi_year.py,sha256=3s4sYWBl9-1rxeTBTMkl5lDeFqCioi4uuxcZlbWmIbE,30998
54
+ reV/handlers/multi_year.py,sha256=nLskop2crDnRfd0DwnFw6SZZBqgiJbf9BABtr7u4j7w,30789
55
55
  reV/handlers/outputs.py,sha256=VbSPFwA0ZH-oWUCCtef7zGyPbWXKY07ilPzpZIOMmuc,6034
56
56
  reV/handlers/transmission.py,sha256=JzpmiweCez7vzGSutO21XIbG9czY_H6ysg_R7z290w0,25610
57
57
  reV/hybrids/__init__.py,sha256=oBrJSt9WeBlER7GVd-NEJgVqFlasl0WuyHJRMgLgpAY,133
@@ -74,24 +74,24 @@ reV/rep_profiles/cli_rep_profiles.py,sha256=i3fRolT7HTzTQePXpNLDyxwgpRa7FEfHO1mO
74
74
  reV/rep_profiles/rep_profiles.py,sha256=oqmtU9FbUlKurkglmZLyDBNH8VRKv8fgdSuvtYWLm04,48271
75
75
  reV/supply_curve/__init__.py,sha256=dbf0cO0qmt1VhV8dnDddztrcpnwua9T2HBhM6tLKaP8,274
76
76
  reV/supply_curve/aggregation.py,sha256=fv4FTdRUQWZ_1Ds84ubgJdrf5lR1xb3luhAnibe3Y3Q,38752
77
- reV/supply_curve/cli_sc_aggregation.py,sha256=drzYGFEHC3Ww1GBnk_iClFoQuXjT3nUEpv8I4Fgx8W4,2867
77
+ reV/supply_curve/cli_sc_aggregation.py,sha256=qGfJyZjg4tFARG2dl-wAlHv9KjEp2u4wg1Boxz18Gf0,3347
78
78
  reV/supply_curve/cli_supply_curve.py,sha256=e-XrHQIe4OqWTL6u-TUAyHrw7Alk7vkXQ2HoLbE3zTM,2163
79
79
  reV/supply_curve/competitive_wind_farms.py,sha256=eOjM72-4oWtsqxB7Wh2gnB2zVAt4LY3iPE_DqWdXbQ4,15795
80
80
  reV/supply_curve/exclusions.py,sha256=4-ZxTO5Vlu03vie0V_74uvdajQfCuC8FE96Pg8I4U_c,42950
81
81
  reV/supply_curve/extent.py,sha256=a31po753hXSxQ8lfcCvpE8hoKc4bY7MmYq0NO0jtdqA,17414
82
82
  reV/supply_curve/points.py,sha256=YEYHpn3KlBbGqpxywrfbrUrlhL3BndgX7cVQerdB6zg,86107
83
- reV/supply_curve/sc_aggregation.py,sha256=6kJg4CaLlFAC196azbfzA-T_wXkXSwNDQKOW-k2lqcE,61645
83
+ reV/supply_curve/sc_aggregation.py,sha256=R_h3xXKum4JTYMuq2us0rWhW0t2wm-G9Wj2on1d8FeY,61604
84
84
  reV/supply_curve/supply_curve.py,sha256=igbloCkvYQwaH4zjbrYO17J7TtCTX5dKkk-TnlGJJeY,69931
85
- reV/supply_curve/tech_mapping.py,sha256=7him2R-8kpigI47ATSN4ncnvzuF_AzeXyrtz_jmzLug,18573
85
+ reV/supply_curve/tech_mapping.py,sha256=nfqPIj9o1pllX3aRC1Hi2KGXYJOYy68Vbvr_1asNmFk,18573
86
86
  reV/utilities/__init__.py,sha256=iOvOuqcXv_WaSP627z2i2wF5820DbUSGRa7lSj23diQ,10534
87
87
  reV/utilities/cli_functions.py,sha256=1_T_sXz0Ct8lW-vOk3mMRcpD6NYsc9cGI7dEujIi9z4,3864
88
88
  reV/utilities/curtailment.py,sha256=fu48Lje-iyd2Awfe-6jFebvgcKSeJ3daNNTqjFI2GvM,4963
89
89
  reV/utilities/exceptions.py,sha256=f7sRGsbFLpmL6Caq_H1cD4GfVhnLMyvYUsLPA1UVDDE,3974
90
90
  reV/utilities/pytest_utils.py,sha256=T22NFEGxPOc9wRwgy0Pt2cHvw3Vam9cKwUj4AkzI7bU,3244
91
91
  reV/utilities/slots.py,sha256=xsw-JuUVZ0YeoCNuwP_HxGNxFMA4xRs1tuImXHIJqaU,2618
92
- NREL_reV-0.9.2.dist-info/LICENSE,sha256=hDwoTANtan2ZpufBlXm5C3W_PJ-mCqItvlcobgjxL7k,1526
93
- NREL_reV-0.9.2.dist-info/METADATA,sha256=eIecsAhbE1ayna5v0f8gIhfDFYeHN_Mgyjdo_uLEATY,10294
94
- NREL_reV-0.9.2.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
95
- NREL_reV-0.9.2.dist-info/entry_points.txt,sha256=KGtPEOQRZMSqKXjjv5jt_T4e4HQN0fHiaGdAWwTtuW4,617
96
- NREL_reV-0.9.2.dist-info/top_level.txt,sha256=S6YF2ZYgXUB6n28SY0K2H8YB9tMJdXQ9CyQbo6VC89M,4
97
- NREL_reV-0.9.2.dist-info/RECORD,,
92
+ NREL_reV-0.9.5.dist-info/LICENSE,sha256=hDwoTANtan2ZpufBlXm5C3W_PJ-mCqItvlcobgjxL7k,1526
93
+ NREL_reV-0.9.5.dist-info/METADATA,sha256=hx7F_iukuZl9zoHjAmjElOamOiFwUJPjVa0r2WpFiUY,10279
94
+ NREL_reV-0.9.5.dist-info/WHEEL,sha256=eOLhNAGa2EW3wWl_TU484h7q1UNgy0JXjjoqKoxAAQc,92
95
+ NREL_reV-0.9.5.dist-info/entry_points.txt,sha256=KGtPEOQRZMSqKXjjv5jt_T4e4HQN0fHiaGdAWwTtuW4,617
96
+ NREL_reV-0.9.5.dist-info/top_level.txt,sha256=S6YF2ZYgXUB6n28SY0K2H8YB9tMJdXQ9CyQbo6VC89M,4
97
+ NREL_reV-0.9.5.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: bdist_wheel (0.43.0)
2
+ Generator: bdist_wheel (0.44.0)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5
 
reV/SAM/SAM.py CHANGED
@@ -195,6 +195,11 @@ class SamResourceRetriever:
195
195
  # make precip rate available for curtailment analysis
196
196
  kwargs["precip_rate"] = True
197
197
 
198
+ sam_configs = project_points.sam_inputs.values()
199
+ needs_wd = any(_sam_config_contains_turbine_layout(sam_config)
200
+ for sam_config in sam_configs)
201
+ kwargs["require_wind_dir"] = needs_wd
202
+
198
203
  elif res_handler == GeothermalResource:
199
204
  args += (project_points.d,)
200
205
 
@@ -922,6 +927,9 @@ class RevPySam(Sam):
922
927
 
923
928
  def _add_cost_defaults(sam_inputs):
924
929
  """Add default values for required cost outputs if they are missing. """
930
+ if sam_inputs.get("__already_added_cost_defaults"):
931
+ return
932
+
925
933
  sam_inputs.setdefault("fixed_charge_rate", None)
926
934
 
927
935
  reg_mult = sam_inputs.setdefault("capital_cost_multiplier", 1)
@@ -938,6 +946,8 @@ def _add_cost_defaults(sam_inputs):
938
946
  else:
939
947
  sam_inputs["capital_cost"] = None
940
948
 
949
+ sam_inputs["__already_added_cost_defaults"] = True
950
+
941
951
 
942
952
  def _add_sys_capacity(sam_inputs):
943
953
  """Add system capacity SAM input if it is missing. """
@@ -954,3 +964,8 @@ def _add_sys_capacity(sam_inputs):
954
964
  cap = sam_inputs.get("nameplate")
955
965
 
956
966
  sam_inputs["system_capacity"] = cap
967
+
968
+
969
+ def _sam_config_contains_turbine_layout(sam_config):
970
+ """Detect wether SAM config contains multiple turbines in layout. """
971
+ return len(sam_config.get("wind_farm_xCoordinates", ())) > 1
reV/SAM/generation.py CHANGED
@@ -1546,23 +1546,6 @@ class Geothermal(AbstractSamGenerationFromWeatherFile):
1546
1546
  - ``conversion_type`` : Integer flag representing the conversion
1547
1547
  plant type. Either Binary (0) or Flash (1). Only values of 0
1548
1548
  or 1 allowed.
1549
- - ``design_temp`` : EGS plant design temperature (in C). Only
1550
- affects EGS runs. This value may be adjusted internally by
1551
- ``reV under the following conditions:
1552
-
1553
- - The design temperature is larger than the resource
1554
- temperature
1555
- - The design temperature is lower than the resource
1556
- temperature by a factor of ``MAX_RT_TO_EGS_RATIO``
1557
-
1558
- If either of these conditions are true, the ``design_temp`` is
1559
- adjusted to match the resource temperature input in order to
1560
- avoid SAM errors.
1561
- - ``set_EGS_PDT_to_RT`` : Boolean flag to set EGS design
1562
- temperature to match the resource temperature input. If this
1563
- is ``True``, the ``design_temp`` input is ignored. This helps
1564
- avoid SAM/GETEM errors when the plant design temperature is
1565
- too high/low compared to the resource temperature.
1566
1549
  - ``geotherm.cost.inj_prod_well_ratio`` : Fraction representing
1567
1550
  the injection to production well ratio (0-1). SAM GUI defaults
1568
1551
  to 0.5 for this value, but it is recommended to set this to
@@ -1632,10 +1615,6 @@ class Geothermal(AbstractSamGenerationFromWeatherFile):
1632
1615
 
1633
1616
  """
1634
1617
 
1635
- # Per Matt Prilliman on 2/22/24, it's unclear where this ratio originates,
1636
- # but SAM errors out if it's exceeded.
1637
- MAX_RT_TO_EGS_RATIO = 1.134324
1638
- """Max value of ``resource_temperature``/``EGS_plan_design_temperature``"""
1639
1618
  MODULE = "geothermal"
1640
1619
  PYSAM = PySamGeothermal
1641
1620
  PYSAM_WEATHER_TAG = "file_name"
@@ -1738,52 +1717,14 @@ class Geothermal(AbstractSamGenerationFromWeatherFile):
1738
1717
  self.sam_sys_inputs["resource_temp"] = val
1739
1718
 
1740
1719
  def _set_egs_plant_design_temperature(self):
1741
- """Set the EGS plant temp to match resource, if necessary"""
1720
+ """Set the EGS plant temp to match resource (avoids cf > 1)"""
1742
1721
  if self.sam_sys_inputs.get("resource_type") != 1:
1743
1722
  return # Not EGS run
1744
1723
 
1745
- set_egs_pdt_to_rt = self.sam_sys_inputs.get("set_EGS_PDT_to_RT", False)
1746
- egs_plant_design_temp = self.sam_sys_inputs.get("design_temp", 0)
1747
1724
  resource_temp = self.sam_sys_inputs["resource_temp"]
1748
-
1749
- if set_egs_pdt_to_rt:
1750
- msg = (
1751
- "Setting EGS plant design temperature ({}C) to match "
1752
- "resource temperature ({}C)".format(
1753
- egs_plant_design_temp, resource_temp
1754
- )
1755
- )
1756
- logger.info(msg)
1757
- self.sam_sys_inputs["design_temp"] = resource_temp
1758
- return
1759
-
1760
- if egs_plant_design_temp > resource_temp:
1761
- msg = (
1762
- "EGS plant design temperature ({}C) exceeds resource "
1763
- "temperature ({}C). Lowering EGS plant design temperature "
1764
- "to match resource temperature".format(
1765
- egs_plant_design_temp, resource_temp
1766
- )
1767
- )
1768
- logger.warning(msg)
1769
- warn(msg)
1770
- self.sam_sys_inputs["design_temp"] = resource_temp
1771
- return
1772
-
1773
- if resource_temp / egs_plant_design_temp > self.MAX_RT_TO_EGS_RATIO:
1774
- msg = (
1775
- "EGS plant design temperature ({}C) is lower than resource "
1776
- "temperature ({}C) by more than a factor of {}. Increasing "
1777
- "EGS plant design temperature to match resource "
1778
- "temperature".format(
1779
- egs_plant_design_temp,
1780
- resource_temp,
1781
- self.MAX_RT_TO_EGS_RATIO,
1782
- )
1783
- )
1784
- logger.warning(msg)
1785
- warn(msg)
1786
- self.sam_sys_inputs["design_temp"] = resource_temp
1725
+ logger.debug("Setting EGS plant design temperature to match "
1726
+ "resource temperature ({}C)".format(resource_temp))
1727
+ self.sam_sys_inputs["design_temp"] = resource_temp
1787
1728
 
1788
1729
  def _set_nameplate_to_match_resource_potential(self, resource):
1789
1730
  """Set the nameplate capacity to match the resource potential."""
reV/bespoke/bespoke.py CHANGED
@@ -20,7 +20,6 @@ import pandas as pd
20
20
  import psutil
21
21
  from rex.joint_pd.joint_pd import JointPD
22
22
  from rex.multi_year_resource import MultiYearWindResource
23
- from rex.renewable_resource import WindResource
24
23
  from rex.utilities.bc_parse_table import parse_bc_table
25
24
  from rex.utilities.execution import SpawnProcessPool
26
25
  from rex.utilities.loggers import create_dirs, log_mem
@@ -55,13 +54,19 @@ class BespokeMultiPlantData:
55
54
  reads to a single HDF5 file.
56
55
  """
57
56
 
58
- def __init__(self, res_fpath, sc_gid_to_hh, sc_gid_to_res_gid):
57
+ def __init__(self, res_fpath, sc_gid_to_hh, sc_gid_to_res_gid,
58
+ pre_load_humidity=False):
59
59
  """Initialize BespokeMultiPlantData
60
60
 
61
61
  Parameters
62
62
  ----------
63
- res_fpath : str
64
- Path to resource h5 file.
63
+ res_fpath : str | list
64
+ Unix shell style path (potentially containing wildcard (*)
65
+ patterns) to a single or multi-file resource file set(s).
66
+ Can also be an explicit list of resource file paths, which
67
+ themselves can contain wildcards. This input must be
68
+ readable by
69
+ :py:class:`rex.multi_year_resource.MultiYearWindResource`.
65
70
  sc_gid_to_hh : dict
66
71
  Dictionary mapping SC GID values to hub-heights. Data for
67
72
  each SC GID will be pulled for the corresponding hub-height
@@ -69,8 +74,11 @@ class BespokeMultiPlantData:
69
74
  sc_gid_to_res_gid : dict
70
75
  Dictionary mapping SC GID values to an iterable oif resource
71
76
  GID values. Resource GID values should correspond to GID
72
- values in teh HDF5 file, so any GID map must be applied
77
+ values in the HDF5 file, so any GID map must be applied
73
78
  before initializing :class`BespokeMultiPlantData`.
79
+ pre_load_humidity : optional, default=False
80
+ Option to pre-load relative humidity data (useful for icing
81
+ runs). If ``False``, relative humidities are not loaded.
74
82
  """
75
83
  self.res_fpath = res_fpath
76
84
  self.sc_gid_to_hh = sc_gid_to_hh
@@ -80,6 +88,8 @@ class BespokeMultiPlantData:
80
88
  self._wind_speeds = None
81
89
  self._temps = None
82
90
  self._pressures = None
91
+ self._relative_humidities = None
92
+ self._pre_load_humidity = pre_load_humidity
83
93
  self._time_index = None
84
94
  self._pre_load_data()
85
95
 
@@ -95,12 +105,7 @@ class BespokeMultiPlantData:
95
105
  }
96
106
 
97
107
  start_time = time.time()
98
- if "*" in self.res_fpath:
99
- handler = MultiYearWindResource
100
- else:
101
- handler = WindResource
102
-
103
- with handler(self.res_fpath) as res:
108
+ with MultiYearWindResource(self.res_fpath) as res:
104
109
  self._wind_dirs = {
105
110
  hh: res[f"winddirection_{hh}m", :, gids]
106
111
  for hh, gids in self.hh_to_res_gids.items()
@@ -118,6 +123,11 @@ class BespokeMultiPlantData:
118
123
  for hh, gids in self.hh_to_res_gids.items()
119
124
  }
120
125
  self._time_index = res.time_index
126
+ if self._pre_load_humidity:
127
+ self._relative_humidities = {
128
+ hh: res["relativehumidity_2m", :, gids]
129
+ for hh, gids in self.hh_to_res_gids.items()
130
+ }
121
131
 
122
132
  logger.debug(
123
133
  f"Data took {(time.time() - start_time) / 60:.2f} " f"min to load"
@@ -140,6 +150,9 @@ class BespokeMultiPlantData:
140
150
  hh = self.sc_gid_to_hh[sc_gid]
141
151
  sc_point_res_gids = sorted(self.sc_gid_to_res_gid[sc_gid])
142
152
  data_inds = np.searchsorted(self.hh_to_res_gids[hh], sc_point_res_gids)
153
+
154
+ rh = (None if not self._pre_load_humidity
155
+ else self._relative_humidities[hh][:, data_inds])
143
156
  return BespokeSinglePlantData(
144
157
  sc_point_res_gids,
145
158
  self._wind_dirs[hh][:, data_inds],
@@ -147,6 +160,7 @@ class BespokeMultiPlantData:
147
160
  self._temps[hh][:, data_inds],
148
161
  self._pressures[hh][:, data_inds],
149
162
  self._time_index,
163
+ rh,
150
164
  )
151
165
 
152
166
 
@@ -159,7 +173,8 @@ class BespokeSinglePlantData:
159
173
  """
160
174
 
161
175
  def __init__(
162
- self, data_inds, wind_dirs, wind_speeds, temps, pressures, time_index
176
+ self, data_inds, wind_dirs, wind_speeds, temps, pressures, time_index,
177
+ relative_humidities=None,
163
178
  ):
164
179
  """Initialize BespokeSinglePlantData
165
180
 
@@ -170,22 +185,41 @@ class BespokeSinglePlantData:
170
185
  the second dimension of `wind_dirs`, `wind_speeds`, `temps`,
171
186
  and `pressures`. The GID value of data_inds[0] should
172
187
  correspond to the `wind_dirs[:, 0]` data, etc.
173
- wind_dirs, wind_speeds, temps, pressures : 2D np.array
174
- Array of wind directions, wind speeds, temperatures, and
188
+ wind_dirs : 2D np.array
189
+ Array of wind directions. Dimensions should be correspond to
190
+ [time, location]. See documentation for `data_inds` for
191
+ required spatial mapping of GID values.
192
+ wind_speeds : 2D np.array
193
+ Array of wind speeds. Dimensions should be correspond to
194
+ [time, location]. See documentation for `data_inds` for
195
+ required spatial mapping of GID values.
196
+ temps : 2D np.array
197
+ Array oftemperatures. Dimensions should be correspond to
198
+ [time, location]. See documentation for `data_inds` for
199
+ required spatial mapping of GID values.
200
+ pressures : 2D np.array
201
+ Array of pressures. Dimensions should be correspond to
175
202
  pressures, respectively. Dimensions should be correspond to
176
203
  [time, location]. See documentation for `data_inds` for
177
204
  required spatial mapping of GID values.
178
205
  time_index : 1D np.array
179
206
  Time index array corresponding to the temporal dimension of
180
207
  the 2D data. Will be exposed directly to user.
181
-
208
+ relative_humidities : 2D np.array, optional
209
+ Array of relative humidities. Dimensions should be
210
+ correspond to [time, location]. See documentation for
211
+ `data_inds` for required spatial mapping of GID values.
212
+ If ``None``, relative_humidities cannot be queried.
182
213
  """
214
+
183
215
  self.data_inds = data_inds
184
216
  self.wind_dirs = wind_dirs
185
217
  self.wind_speeds = wind_speeds
186
218
  self.temps = temps
187
219
  self.pressures = pressures
188
220
  self.time_index = time_index
221
+ self.relative_humidities = relative_humidities
222
+ self._humidities_exist = relative_humidities is not None
189
223
 
190
224
  def __getitem__(self, key):
191
225
  dset_name, t_idx, gids = key
@@ -198,6 +232,8 @@ class BespokeSinglePlantData:
198
232
  return self.temps[t_idx, data_inds]
199
233
  if "pressure" in dset_name:
200
234
  return self.pressures[t_idx, data_inds]
235
+ if self._humidities_exist and "relativehumidity" in dset_name:
236
+ return self.relative_humidities[t_idx, data_inds]
201
237
  msg = f"Unknown dataset name: {dset_name!r}"
202
238
  logger.error(msg)
203
239
  raise ValueError(msg)
@@ -481,8 +517,7 @@ class BespokeSinglePlant:
481
517
  self._pre_loaded_data = pre_loaded_data
482
518
  self._outputs = {}
483
519
 
484
- Handler = self.get_wind_handler(res)
485
- res = res if not isinstance(res, str) else Handler(res)
520
+ res = res if not isinstance(res, str) else MultiYearWindResource(res)
486
521
 
487
522
  self._sc_point = AggSCPoint(
488
523
  gid,
@@ -713,6 +748,7 @@ class BespokeSinglePlant:
713
748
  weights[i] = self.sc_point.include_mask_flat[mask].sum()
714
749
 
715
750
  weights /= weights.sum()
751
+ data = data.astype(np.float32)
716
752
  data *= weights
717
753
  data = np.sum(data, axis=1)
718
754
 
@@ -898,15 +934,18 @@ class BespokeSinglePlant:
898
934
  if np.nanmax(pres) > 1000:
899
935
  pres *= 9.86923e-6
900
936
 
901
- self._res_df = pd.DataFrame(
902
- {
903
- "temperature": temp,
904
- "pressure": pres,
905
- "windspeed": ws,
906
- "winddirection": wd,
907
- },
908
- index=ti,
909
- )
937
+ data = {
938
+ "temperature": temp,
939
+ "pressure": pres,
940
+ "windspeed": ws,
941
+ "winddirection": wd,
942
+ }
943
+
944
+ if self.sam_sys_inputs.get("en_icing_cutoff"):
945
+ rh = self.get_weighted_res_ts("relativehumidity_2m")
946
+ data["relativehumidity"] = rh
947
+
948
+ self._res_df = pd.DataFrame(data, index=ti)
910
949
 
911
950
  if "time_index_step" in self.original_sam_sys_inputs:
912
951
  ti_step = self.original_sam_sys_inputs["time_index_step"]
@@ -1142,29 +1181,6 @@ class BespokeSinglePlant:
1142
1181
  lcoe_kwargs["capital_cost"] = lcoe_kwargs["capital_cost"] + bos
1143
1182
  return lcoe_kwargs
1144
1183
 
1145
- @staticmethod
1146
- def get_wind_handler(res):
1147
- """Get a wind resource handler for a resource filepath.
1148
-
1149
- Parameters
1150
- ----------
1151
- res : str
1152
- Resource filepath to wtk .h5 file. Can include * wildcards
1153
- for multi year resource.
1154
-
1155
- Returns
1156
- -------
1157
- handler : WindResource | MultiYearWindResource
1158
- Wind resource handler or multi year handler
1159
- """
1160
- handler = res
1161
- if isinstance(res, str):
1162
- if "*" in res:
1163
- handler = MultiYearWindResource
1164
- else:
1165
- handler = WindResource
1166
- return handler
1167
-
1168
1184
  @classmethod
1169
1185
  def check_dependencies(cls):
1170
1186
  """Check special dependencies for bespoke"""
@@ -1382,32 +1398,45 @@ class BespokeSinglePlant:
1382
1398
  eos_mult = (self.plant_optimizer.capital_cost
1383
1399
  / self.plant_optimizer.capacity
1384
1400
  / baseline_cost)
1385
- reg_mult = self.sam_sys_inputs.get("capital_cost_multiplier", 1)
1401
+ reg_mult_cc = self.sam_sys_inputs.get(
1402
+ "capital_cost_multiplier", 1)
1403
+ reg_mult_foc = self.sam_sys_inputs.get(
1404
+ "fixed_operating_cost_multiplier", 1)
1405
+ reg_mult_voc = self.sam_sys_inputs.get(
1406
+ "variable_operating_cost_multiplier", 1)
1407
+ reg_mult_bos = self.sam_sys_inputs.get(
1408
+ "balance_of_system_cost_multiplier", 1)
1386
1409
 
1387
1410
  self._meta[SupplyCurveField.EOS_MULT] = eos_mult
1388
- self._meta[SupplyCurveField.REG_MULT] = reg_mult
1411
+ self._meta[SupplyCurveField.REG_MULT] = reg_mult_cc
1389
1412
 
1390
- cap_cost = (
1391
- self.plant_optimizer.capital_cost
1392
- + self.plant_optimizer.balance_of_system_cost
1393
- )
1394
1413
  self._meta[SupplyCurveField.COST_SITE_OCC_USD_PER_AC_MW] = (
1395
- cap_cost / capacity_ac_mw
1414
+ (self.plant_optimizer.capital_cost
1415
+ + self.plant_optimizer.balance_of_system_cost)
1416
+ / capacity_ac_mw
1396
1417
  )
1397
1418
  self._meta[SupplyCurveField.COST_BASE_OCC_USD_PER_AC_MW] = (
1398
- cap_cost / eos_mult / reg_mult / capacity_ac_mw
1419
+ (self.plant_optimizer.capital_cost / eos_mult / reg_mult_cc
1420
+ + self.plant_optimizer.balance_of_system_cost / reg_mult_bos)
1421
+ / capacity_ac_mw
1399
1422
  )
1400
1423
  self._meta[SupplyCurveField.COST_SITE_FOC_USD_PER_AC_MW] = (
1401
- self.plant_optimizer.fixed_operating_cost / capacity_ac_mw
1424
+ self.plant_optimizer.fixed_operating_cost
1425
+ / capacity_ac_mw
1402
1426
  )
1403
1427
  self._meta[SupplyCurveField.COST_BASE_FOC_USD_PER_AC_MW] = (
1404
- self.plant_optimizer.fixed_operating_cost / capacity_ac_mw
1428
+ self.plant_optimizer.fixed_operating_cost
1429
+ / reg_mult_foc
1430
+ / capacity_ac_mw
1405
1431
  )
1406
1432
  self._meta[SupplyCurveField.COST_SITE_VOC_USD_PER_AC_MW] = (
1407
- self.plant_optimizer.variable_operating_cost / capacity_ac_mw
1433
+ self.plant_optimizer.variable_operating_cost
1434
+ / capacity_ac_mw
1408
1435
  )
1409
1436
  self._meta[SupplyCurveField.COST_BASE_VOC_USD_PER_AC_MW] = (
1410
- self.plant_optimizer.variable_operating_cost / capacity_ac_mw
1437
+ self.plant_optimizer.variable_operating_cost
1438
+ / reg_mult_voc
1439
+ / capacity_ac_mw
1411
1440
  )
1412
1441
  self._meta[SupplyCurveField.FIXED_CHARGE_RATE] = (
1413
1442
  self.plant_optimizer.fixed_charge_rate
@@ -1489,8 +1518,9 @@ class BespokeWindPlants(BaseAggregation):
1489
1518
  ws_bins=(0.0, 20.0, 5.0), wd_bins=(0.0, 360.0, 45.0),
1490
1519
  excl_dict=None, area_filter_kernel='queen', min_area=None,
1491
1520
  resolution=64, excl_area=None, data_layers=None,
1492
- pre_extract_inclusions=False, prior_run=None, gid_map=None,
1493
- bias_correct=None, pre_load_data=False):
1521
+ pre_extract_inclusions=False, eos_mult_baseline_cap_mw=200,
1522
+ prior_run=None, gid_map=None, bias_correct=None,
1523
+ pre_load_data=False):
1494
1524
  """reV bespoke analysis class.
1495
1525
 
1496
1526
  Much like generation, ``reV`` bespoke analysis runs SAM
@@ -1521,14 +1551,15 @@ class BespokeWindPlants(BaseAggregation):
1521
1551
  uniquely defined (i.e.only appear once and in a single
1522
1552
  input file).
1523
1553
  res_fpath : str
1524
- Filepath to wind resource data in NREL WTK format. This
1525
- input can be path to a single resource HDF5 file or a path
1526
- including a wildcard input like ``/h5_dir/prefix*suffix`` to
1527
- run bespoke on multiple years of resource data. The former
1528
- must be readable by
1529
- :py:class:`rex.renewable_resource.WindResource` while the
1530
- latter must be readable by
1531
- or :py:class:`rex.multi_year_resource.MultiYearWindResource`
1554
+ Unix shell style path to wind resource HDF5 file in NREL WTK
1555
+ format. Can also be a path including a wildcard input like
1556
+ ``/h5_dir/prefix*suffix`` to run bespoke on multiple years
1557
+ of resource data. Can also be an explicit list of resource
1558
+ HDF5 file paths, which themselves can contain wildcards. If
1559
+ multiple files are specified in this way, they must have the
1560
+ same coordinates but can have different time indices (i.e.
1561
+ different years). This input must be readable by
1562
+ :py:class:`rex.multi_year_resource.MultiYearWindResource`
1532
1563
  (i.e. the resource data conform to the
1533
1564
  `rex data format <https://tinyurl.com/3fy7v5kx>`_). This
1534
1565
  means the data file(s) must contain a 1D ``time_index``
@@ -1855,6 +1886,13 @@ class BespokeWindPlants(BaseAggregation):
1855
1886
  the `excl_dict` input. It is typically faster to compute
1856
1887
  the inclusion mask on the fly with parallel workers.
1857
1888
  By default, ``False``.
1889
+ eos_mult_baseline_cap_mw : int | float, optional
1890
+ Baseline plant capacity (MW) used to calculate economies of
1891
+ scale (EOS) multiplier from the `capital_cost_function`. EOS
1892
+ multiplier is calculated as the $-per-kW of the wind plant
1893
+ divided by the $-per-kW of a plant with this baseline
1894
+ capacity. By default, `200` (MW), which aligns the baseline
1895
+ with ATB assumptions. See here: https://tinyurl.com/y85hnu6h.
1858
1896
  prior_run : str, optional
1859
1897
  Optional filepath to a bespoke output HDF5 file belonging to
1860
1898
  a prior run. If specified, this module will only run the
@@ -1980,6 +2018,7 @@ class BespokeWindPlants(BaseAggregation):
1980
2018
  self._ws_bins = ws_bins
1981
2019
  self._wd_bins = wd_bins
1982
2020
  self._data_layers = data_layers
2021
+ self._eos_mult_baseline_cap_mw = eos_mult_baseline_cap_mw
1983
2022
  self._prior_meta = self._parse_prior_run(prior_run)
1984
2023
  self._gid_map = BespokeSinglePlant._parse_gid_map(gid_map)
1985
2024
  self._bias_correct = Gen._parse_bc(bias_correct)
@@ -2119,8 +2158,7 @@ class BespokeWindPlants(BaseAggregation):
2119
2158
  )
2120
2159
 
2121
2160
  # just check that this file exists, cannot check res_fpath if *glob
2122
- Handler = BespokeSinglePlant.get_wind_handler(self._res_fpath)
2123
- with Handler(self._res_fpath) as f:
2161
+ with MultiYearWindResource(self._res_fpath) as f:
2124
2162
  assert any(f.dsets)
2125
2163
 
2126
2164
  def _pre_load_data(self, pre_load_data):
@@ -2159,7 +2197,10 @@ class BespokeWindPlants(BaseAggregation):
2159
2197
 
2160
2198
  logger.info("Pre-loading resource data for Bespoke run... ")
2161
2199
  self._pre_loaded_data = BespokeMultiPlantData(
2162
- self._res_fpath, sc_gid_to_hh, sc_gid_to_res_gid
2200
+ self._res_fpath,
2201
+ sc_gid_to_hh,
2202
+ sc_gid_to_res_gid,
2203
+ pre_load_humidity=self._project_points.sam_config_obj.icing,
2163
2204
  )
2164
2205
 
2165
2206
  def _hh_for_sc_gid(self, sc_gid):
@@ -2453,8 +2494,8 @@ class BespokeWindPlants(BaseAggregation):
2453
2494
  area_filter_kernel='queen', min_area=None,
2454
2495
  resolution=64, excl_area=0.0081, data_layers=None,
2455
2496
  gids=None, exclusion_shape=None, slice_lookup=None,
2456
- prior_meta=None, gid_map=None, bias_correct=None,
2457
- pre_loaded_data=None):
2497
+ eos_mult_baseline_cap_mw=200, prior_meta=None,
2498
+ gid_map=None, bias_correct=None, pre_loaded_data=None):
2458
2499
  """
2459
2500
  Standalone serial method to run bespoke optimization.
2460
2501
  See BespokeWindPlants docstring for parameter description.
@@ -2480,14 +2521,13 @@ class BespokeWindPlants(BaseAggregation):
2480
2521
  exclusion_shape = sc.exclusions.shape
2481
2522
 
2482
2523
  cls._check_inclusion_mask(inclusion_mask, gids, exclusion_shape)
2483
- Handler = BespokeSinglePlant.get_wind_handler(res_fpath)
2484
2524
 
2485
2525
  # pre-extract handlers so they are not repeatedly initialized
2486
2526
  file_kwargs = {
2487
2527
  "excl_dict": excl_dict,
2488
2528
  "area_filter_kernel": area_filter_kernel,
2489
2529
  "min_area": min_area,
2490
- "h5_handler": Handler,
2530
+ "h5_handler": MultiYearWindResource,
2491
2531
  }
2492
2532
 
2493
2533
  with AggFileHandler(excl_fpath, res_fpath, **file_kwargs) as fh:
@@ -2520,6 +2560,7 @@ class BespokeWindPlants(BaseAggregation):
2520
2560
  excl_area=excl_area,
2521
2561
  data_layers=data_layers,
2522
2562
  exclusion_shape=exclusion_shape,
2563
+ eos_mult_baseline_cap_mw=eos_mult_baseline_cap_mw,
2523
2564
  prior_meta=prior_meta,
2524
2565
  gid_map=gid_map,
2525
2566
  bias_correct=bias_correct,
@@ -2612,6 +2653,7 @@ class BespokeWindPlants(BaseAggregation):
2612
2653
  gids=gid,
2613
2654
  exclusion_shape=self.shape,
2614
2655
  slice_lookup=copy.deepcopy(self.slice_lookup),
2656
+ eos_mult_baseline_cap_mw=self._eos_mult_baseline_cap_mw,
2615
2657
  prior_meta=self._get_prior_meta(gid),
2616
2658
  gid_map=self._gid_map,
2617
2659
  bias_correct=self._get_bc_for_gid(gid),
@@ -2676,6 +2718,7 @@ class BespokeWindPlants(BaseAggregation):
2676
2718
  afk = self._area_filter_kernel
2677
2719
  wlm = self._wake_loss_multiplier
2678
2720
  i_bc = self._get_bc_for_gid(gid)
2721
+ ebc = self._eos_mult_baseline_cap_mw
2679
2722
 
2680
2723
  si = self.run_serial(self._excl_fpath,
2681
2724
  self._res_fpath,
@@ -2700,6 +2743,7 @@ class BespokeWindPlants(BaseAggregation):
2700
2743
  excl_area=self._excl_area,
2701
2744
  data_layers=self._data_layers,
2702
2745
  slice_lookup=slice_lookup,
2746
+ eos_mult_baseline_cap_mw=ebc,
2703
2747
  prior_meta=prior_meta,
2704
2748
  gid_map=self._gid_map,
2705
2749
  bias_correct=i_bc,
@@ -236,10 +236,10 @@ class Gen(BaseGen):
236
236
  info on the allowed and/or required SAM config file inputs.
237
237
  resource_file : str
238
238
  Filepath to resource data. This input can be path to a
239
- single resource HDF5 file, a path to a directory containing
240
- data spread across multiple HDF5 files, or a path including
241
- a wildcard input like ``/h5_dir/prefix*suffix``. In all
242
- cases, the resource data must be readable by
239
+ single resource HDF5 file or a path including a wildcard
240
+ input like ``/h5_dir/prefix*suffix`` (i.e. if your datasets
241
+ for a single year are spread out over multiple files). In
242
+ all cases, the resource data must be readable by
243
243
  :py:class:`rex.resource.Resource`
244
244
  or :py:class:`rex.multi_file_resource.MultiFileResource`.
245
245
  (i.e. the resource data conform to the
@@ -253,8 +253,14 @@ class Gen(BaseGen):
253
253
  consideration, and its shape must be a multiple of 8760.
254
254
 
255
255
  .. Note:: If executing ``reV`` from the command line, this
256
- path can contain brackets ``{}`` that will be filled in by
257
- the `analysis_years` input.
256
+ input string can contain brackets ``{}`` that will be
257
+ filled in by the `analysis_years` input. Alternatively,
258
+ this input can be a list of explicit files to process. In
259
+ this case, the length of the list must match the length of
260
+ the `analysis_years` input exactly, and the path are
261
+ assumed to align with the `analysis_years` (i.e. the first
262
+ path corresponds to the first analysis year, the second
263
+ path corresponds to the second analysis year, and so on).
258
264
 
259
265
  .. Important:: If you are using custom resource data (i.e.
260
266
  not NSRDB/WTK/Sup3rCC, etc.), ensure the following:
@@ -96,15 +96,17 @@ class MultiYearGroup:
96
96
  pass_through_dsets : list
97
97
  List of pass through datasets.
98
98
  """
99
+ with Resource(self.source_files[0]) as res:
100
+ all_dsets = res.datasets
101
+
99
102
  if isinstance(dsets, str) and dsets == 'PIPELINE':
100
- files = parse_previous_status(self._dirout, ModuleName.MULTI_YEAR)
101
- with Resource(files[0]) as res:
102
- dsets = res.datasets
103
+ dsets = all_dsets
103
104
 
104
105
  if "lcoe_fcr" in dsets:
105
106
  for dset in LCOE_REQUIRED_OUTPUTS:
106
- if dset not in pass_through_dsets:
107
+ if dset not in pass_through_dsets and dset in all_dsets:
107
108
  pass_through_dsets.append(dset)
109
+
108
110
  if "dc_ac_ratio" in dsets:
109
111
  if "dc_ac_ratio" not in pass_through_dsets:
110
112
  pass_through_dsets.append("dc_ac_ratio")
@@ -839,11 +841,6 @@ def my_collect_groups(out_fpath, groups, clobber=True):
839
841
  dset, group=group['group'])
840
842
 
841
843
  pass_through_dsets = group.get('pass_through_dsets') or []
842
- if "lcoe_fcr" in group['dsets']:
843
- for dset in LCOE_REQUIRED_OUTPUTS:
844
- if dset not in pass_through_dsets:
845
- pass_through_dsets.append(dset)
846
-
847
844
  for dset in pass_through_dsets:
848
845
  MultiYear.pass_through(out_fpath, group['source_files'],
849
846
  dset, group=group['group'])
@@ -50,12 +50,25 @@ def _preprocessor(config, out_dir):
50
50
  def _format_res_fpath(config):
51
51
  """Format res_fpath with year, if need be. """
52
52
  res_fpath = config.setdefault("res_fpath", None)
53
- if isinstance(res_fpath, str) and '{}' in res_fpath:
54
- for year in range(1998, 2018):
55
- if os.path.exists(res_fpath.format(year)):
56
- break
57
-
58
- config["res_fpath"] = res_fpath.format(year)
53
+ if isinstance(res_fpath, str):
54
+ if '{}' in res_fpath:
55
+ for year in range(1950, 2100):
56
+ if os.path.exists(res_fpath.format(year)):
57
+ break
58
+ else:
59
+ msg = ("Could not find any files that match the pattern"
60
+ "{!r}".format(res_fpath.format("<year>")))
61
+ logger.error(msg)
62
+ raise FileNotFoundError(msg)
63
+
64
+ res_fpath = res_fpath.format(year)
65
+
66
+ elif not os.path.exists(res_fpath):
67
+ msg = "Could not find resource file: {!r}".format(res_fpath)
68
+ logger.error(msg)
69
+ raise FileNotFoundError(msg)
70
+
71
+ config["res_fpath"] = res_fpath
59
72
 
60
73
  return config
61
74
 
@@ -18,7 +18,6 @@ from rex.multi_file_resource import MultiFileResource
18
18
  from rex.resource import Resource
19
19
  from rex.utilities.execution import SpawnProcessPool
20
20
 
21
- from reV.generation.base import BaseGen
22
21
  from reV.handlers.exclusions import ExclusionLayers
23
22
  from reV.supply_curve.aggregation import (
24
23
  AbstractAggFileHandler,
@@ -1410,7 +1409,7 @@ class SupplyCurveAggregation(BaseAggregation):
1410
1409
  ``multi-year``, ``collect``, or ``econ``. However, note
1411
1410
  that duplicate executions of any of these commands within
1412
1411
  the pipeline may invalidate this parsing, meaning the
1413
- `econ_fpath` input will have to be specified manually.
1412
+ `gen_fpath` input will have to be specified manually.
1414
1413
 
1415
1414
  By default, ``None``.
1416
1415
  args : tuple | list, optional
@@ -185,7 +185,7 @@ class TechMapping:
185
185
  excl_row_slices, excl_col_slices,
186
186
  coord_labels=(LATITUDE, LONGITUDE)):
187
187
  """
188
- Extract the exclusion coordinates for teh desired gids for TechMapping.
188
+ Extract the exclusion coordinates for the desired gids for TechMapping.
189
189
 
190
190
  Parameters
191
191
  ----------
reV/version.py CHANGED
@@ -2,4 +2,4 @@
2
2
  reV Version number
3
3
  """
4
4
 
5
- __version__ = "0.9.2"
5
+ __version__ = "0.9.5"