From 87a2927971ed2e87001673088dbb913ce66361ef Mon Sep 17 00:00:00 2001 From: Steven Janzou Date: Sun, 23 Apr 2023 04:37:24 -0600 Subject: [PATCH] add adjustment factors back to cmod_windpower, add hourly adjustment factors back --- ssc/cmod_pvsamv1.cpp | 2 +- ssc/cmod_pvwattsv7.cpp | 5 +---- ssc/cmod_pvwattsv8.cpp | 7 ++----- ssc/cmod_windpower.cpp | 13 ++++++------- ssc/common.cpp | 25 +++++++++++++++++++++++++ test/input_cases/pvyield_common_data.h | 16 ++++++++-------- 6 files changed, 43 insertions(+), 25 deletions(-) diff --git a/ssc/cmod_pvsamv1.cpp b/ssc/cmod_pvsamv1.cpp index 14266c594..0a14e701d 100644 --- a/ssc/cmod_pvsamv1.cpp +++ b/ssc/cmod_pvsamv1.cpp @@ -1127,7 +1127,7 @@ void cm_pvsamv1::exec() { for (size_t nn = 0; nn < num_subarrays; nn++) { - if (is_assigned("subarray" + util::to_string(static_cast(nn + 1)) + "_shading:timestep")) + if (is_assigned("subarray" + util::to_string(static_cast(nn + 1)) + "_shading_timestep")) throw exec_error("pvsamv1", "Time series beam shading inputs cannot be used for a simulation period that is not continuous over one or more years."); } } diff --git a/ssc/cmod_pvwattsv7.cpp b/ssc/cmod_pvwattsv7.cpp index 87ccb1fd2..f956a20ee 100644 --- a/ssc/cmod_pvwattsv7.cpp +++ b/ssc/cmod_pvwattsv7.cpp @@ -613,12 +613,9 @@ class cm_pvwattsv7 : public compute_module // read all the shading input data and calculate the hourly factors for use subsequently // timeseries beam shading factors cannot be used with non-annual data - if (is_assigned("shading")) { - auto& table = get_var_table()->lookup("shading")->table; - if (table.is_assigned("en_timestep") && table.as_boolean("en_timestep") && !wdprov->annualSimulation()) + if (is_assigned("shading_en_timestep") && as_boolean("shading_en_timestep") && !wdprov->annualSimulation()) // if (is_assigned("shading:timestep") && !wdprov->annualSimulation()) throw exec_error("pvwattsv7", "Timeseries beam shading inputs cannot be used for a simulation period that is not continuous over one or more years."); - } shading_factor_calculator shad; if (!shad.setup(this, "")) throw exec_error("pvwattsv7", shad.get_error()); diff --git a/ssc/cmod_pvwattsv8.cpp b/ssc/cmod_pvwattsv8.cpp index 309e09550..a295fc72d 100644 --- a/ssc/cmod_pvwattsv8.cpp +++ b/ssc/cmod_pvwattsv8.cpp @@ -669,12 +669,9 @@ class cm_pvwattsv8 : public compute_module // read all the shading input data and calculate the hourly factors for use subsequently // timeseries beam shading factors cannot be used with non-annual data - if (is_assigned("shading")) { - auto& table = get_var_table()->lookup("shading")->table; - if (table.is_assigned("en_timestep") && table.as_boolean("en_timestep") && !wdprov->annualSimulation()) - // if (is_assigned("shading:timestep") && !wdprov->annualSimulation()) + if (is_assigned("shading_en_timestep") && as_boolean("shading_en_timestep") && !wdprov->annualSimulation()) + // if (is_assigned("shading:timestep") && !wdprov->annualSimulation()) throw exec_error("pvwattsv8", "Timeseries beam shading inputs cannot be used for a simulation period that is not continuous over one or more years."); - } shading_factor_calculator shad; if (!shad.setup(this, "")) throw exec_error("pvwattsv8", shad.get_error()); diff --git a/ssc/cmod_windpower.cpp b/ssc/cmod_windpower.cpp index 4c0db9a3e..fd5e4491b 100644 --- a/ssc/cmod_windpower.cpp +++ b/ssc/cmod_windpower.cpp @@ -222,7 +222,7 @@ bool winddata::read_line(std::vector &values) cm_windpower::cm_windpower(){ add_var_info(_cm_vtab_windpower); // performance adjustment factors - //add_var_info(vtab_adjustment_factors); unused and defaults have all set to zero + add_var_info(vtab_adjustment_factors); add_var_info(vtab_technology_outputs); // wind PRUF add_var_info(vtab_p50p90); @@ -310,12 +310,11 @@ void cm_windpower::exec() } if (wpc.nTurbines > wpc.GetMaxTurbines()) throw exec_error("windpower", util::format("the wind model is only configured to handle up to %d turbines.", wpc.GetMaxTurbines())); -/*Unused in last two release and no input widget + // create adjustment factors and losses adjustment_factors haf(this, "adjust"); if (!haf.setup()) throw exec_error("windpower", "failed to setup adjustment factors: " + haf.error()); -*/ // add up all the percent losses, except for wind_int_loss, which will be applied by the turbine double lossMultiplier = get_fixed_losses(this); @@ -357,7 +356,7 @@ void cm_windpower::exec() for (int i = 0; i < nstep; i++) //nstep is always 8760 for Weibull { farmpwr[i] = farm_kw; // fill "gen" -// farmpwr[i] *= haf(i); //apply adjustment factor/availability and curtailment losses + farmpwr[i] *= haf(i); //apply adjustment factor/availability and curtailment losses } for (size_t i = 0; i < wpc.nTurbines; i++) @@ -420,7 +419,7 @@ void cm_windpower::exec() for (int i = 0; i < nstep; i++) { farmpwr[i] = farm_kw; // fill "gen" -// farmpwr[i] *= haf(i); //apply adjustment factor/availability and curtailment losses + farmpwr[i] *= haf(i); //apply adjustment factor/availability and curtailment losses farmpwr[i] *= lossMultiplier; } @@ -601,7 +600,7 @@ void cm_windpower::exec() annual_after_wake_loss += farmp; farmp *= lossMultiplier; // apply and track cutoff losses - withoutCutOffLosses += farmp; // *haf(hr); + withoutCutOffLosses += farmp * haf(hr); if (lowTempCutoff){ if (temp < lowTempCutoffValue) farmp = 0.0; } @@ -610,7 +609,7 @@ void cm_windpower::exec() farmp = 0.0; } - farmpwr[i] = (ssc_number_t)farmp;// *haf(hr); //adjustment factors are constrained to be hourly, not sub-hourly, so it's correct for this to be indexed on the hour + farmpwr[i] = (ssc_number_t)farmp*haf(hr); //adjustment factors are constrained to be hourly, not sub-hourly, so it's correct for this to be indexed on the hour wspd[i] = (ssc_number_t)wind; wdir[i] = (ssc_number_t)dir; air_temp[i] = (ssc_number_t)temp; diff --git a/ssc/common.cpp b/ssc/common.cpp index 2ecbd5900..edefee575 100644 --- a/ssc/common.cpp +++ b/ssc/common.cpp @@ -522,6 +522,10 @@ var_info vtab_adjustment_factors[] = { "'adjust' and 'en_timeindex' separated by _ instead of : after SAM 2022.12.21", "Adjustment Factors", "?=0", "BOOLEAN", "" }, { SSC_INPUT, SSC_NUMBER, "adjust_en_periods" , "Enable period-based adjustment factors", "0/1", "'adjust' and 'en_periods' separated by _ instead of : after SAM 2022.12.21", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT, SSC_NUMBER, "adjust_en_hourly" , "Enable hourly-based adjustment factors", "0/1", +"'adjust' and 'en_hourly' separated by _ instead of : after SAM 2022.12.21", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT,SSC_ARRAY , "adjust_hourly" , "Hourly adjustment factors" , "%", +"'adjust' and 'timeindex' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "adjust_en_hourly=1" , "LENGTH=8760" , ""}, { SSC_INPUT,SSC_ARRAY , "adjust_timeindex" , "Lifetime adjustment factors" , "%", "'adjust' and 'timeindex' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "adjust_en_timeindex=1" , "" , ""}, { SSC_INPUT,SSC_MATRIX , "adjust_periods" , "Period-based adjustment factors" , "%", @@ -533,6 +537,10 @@ var_info vtab_dc_adjustment_factors[] = { "'dc_adjust' and 'constant' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "*" , "MAX=100" , ""}, { SSC_INPUT, SSC_NUMBER, "dc_adjust_en_timeindex" , "Enable lifetime adjustment factors", "0/1", "", "Adjustment Factors", "?=0", "BOOLEAN", "" }, { SSC_INPUT, SSC_NUMBER, "dc_adjust_en_periods" , "Enable period-based adjustment factors", "0/1", "", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT, SSC_NUMBER, "dc_adjust_en_hourly" , "Enable hourly-based adjustment factors", "0/1", +"'dc_adjust' and 'en_hourly' separated by _ instead of : after SAM 2022.12.21", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT,SSC_ARRAY , "dc_adjust_hourly" , "DC Hourly adjustment factors" , "%", +"'dc_adjust' and 'timeindex' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "dc_adjust_en_hourly=1" , "LENGTH=8760" , ""}, { SSC_INPUT,SSC_ARRAY , "dc_adjust_timeindex" , "DC Lifetime Adjustment Factors" , "%" , "" , "Adjustment Factors" , "dc_adjust_en_timeindex=1" , "" , ""}, { SSC_INPUT,SSC_MATRIX , "dc_adjust_periods" , "DC Period-based Adjustment Factors" , "%" , "n x 3 matrix [ start, end, loss ]" , "Adjustment Factors" , "dc_adjust_en_periods=1" , "COLS=3" , ""}, var_info_invalid }; @@ -542,6 +550,10 @@ var_info vtab_sf_adjustment_factors[] = { "'sf_adjust' and 'constant' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "*" , "MAX=100" , ""}, { SSC_INPUT, SSC_NUMBER, "sf_adjust_en_timeindex" , "Enable lifetime adjustment factors", "0/1", "", "Adjustment Factors", "?=0", "BOOLEAN", "" }, { SSC_INPUT, SSC_NUMBER, "sf_adjust_en_periods" , "Enable period-based adjustment factors", "0/1", "", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT, SSC_NUMBER, "sf_adjust_en_hourly" , "Enable hourly-based adjustment factors", "0/1", +"'adjust' and 'en_hourly' separated by _ instead of : after SAM 2022.12.21", "Adjustment Factors", "?=0", "BOOLEAN", "" }, +{ SSC_INPUT,SSC_ARRAY , "sf_adjust_hourly" , "SF Hourly adjustment factors" , "%", +"'adjust' and 'timeindex' separated by _ instead of : after SAM 2022.12.21" , "Adjustment Factors" , "sf_adjust_en_hourly=1" , "LENGTH=8760" , ""}, { SSC_INPUT,SSC_ARRAY , "sf_adjust_timeindex" , "SF Lifetime Adjustment Factors" , "%" , "" , "Adjustment Factors" , "sf_adjust_en_timeindex=1" , "" , ""}, { SSC_INPUT,SSC_MATRIX , "sf_adjust_periods" , "SF Period-based Adjustment Factors" , "%" , "n x 3 matrix [ start, end, loss ]" , "Adjustment Factors" , "sf_adjust_en_periods=1" , "COLS=3" , ""}, var_info_invalid }; @@ -1022,6 +1034,19 @@ bool adjustment_factors::setup(int nsteps, int analysis_period) //nsteps is set f = 1.0 - f / 100.0; //convert from percentage to factor m_factors.resize( nsteps * analysis_period, f); + if ( m_cm->as_boolean(m_prefix + "_en_hourly")) + { + size_t n; + ssc_number_t *p = m_cm->as_array( m_prefix + "_hourly", &n ); + if ( p != 0 && n == 8760 ) + { + for( int i=0;i<8760;i++ ) + m_factors[i] *= (1.0 - p[i]/100.0); //convert from percentages to factors + } + else { + m_error = util::format("Hourly loss factor array length %d does not equal length of weather file %d", (int)n, nsteps); + } + } if (m_cm->as_boolean(m_prefix + "_en_timeindex")) { size_t n; diff --git a/test/input_cases/pvyield_common_data.h b/test/input_cases/pvyield_common_data.h index 707924fa9..19397d036 100644 --- a/test/input_cases/pvyield_common_data.h +++ b/test/input_cases/pvyield_common_data.h @@ -492,8 +492,8 @@ void pvyield_no_financial_meteo(ssc_data_t& data) // shading inputs from Timo - ssc_data_set_number(data, "subarray1_shading:string_option", -1); - ssc_data_set_number(data, "subarray1_shading:diff", 0); + ssc_data_set_number(data, "subarray1_shading_string_option", -1); + ssc_data_set_number(data, "subarray1_shading_diff", 0); @@ -933,8 +933,8 @@ void pvyield_bifacial_case(ssc_data_t& data) ssc_data_set_string(data, "ond_ModeAffEnum", "Efficiencyf_PIn"); // shading inputs from Timo - ssc_data_set_number(data, "subarray1_shading:string_option", -1); - ssc_data_set_number(data, "subarray1_shading:diff", 0); + ssc_data_set_number(data, "subarray1_shading_string_option", -1); + ssc_data_set_number(data, "subarray1_shading_diff", 0); } void pvyield_user_support_80603_meteo(ssc_data_t& data) @@ -1370,8 +1370,8 @@ void pvyield_user_support_80603_meteo(ssc_data_t& data) ssc_data_set_string(data, "ond_ModeAffEnum", "Efficiencyf_PIn"); // shading inputs from Timo - ssc_data_set_number(data, "subarray1_shading:string_option", -1); - ssc_data_set_number(data, "subarray1_shading:diff", 0); + ssc_data_set_number(data, "subarray1_shading_string_option", -1); + ssc_data_set_number(data, "subarray1_shading_diff", 0); } @@ -1809,8 +1809,8 @@ void pvyield_user_support_80603_AZ(ssc_data_t& data) // shading inputs from Timo - ssc_data_set_number(data, "subarray1_shading:string_option", -1); - ssc_data_set_number(data, "subarray1_shading:diff", 0); + ssc_data_set_number(data, "subarray1_shading_string_option", -1); + ssc_data_set_number(data, "subarray1_shading_diff", 0); }