Skip to content

Commit 3661367

Browse files
committed
Solar calc reorg WIP; test ref files updated
1 parent 05da792 commit 3661367

29 files changed

+17802
-17741
lines changed

src/CGSOLAR.CPP

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -418,8 +418,9 @@ void FC makHrSgt( // make solar tables for an hour for current month
418418
// Re-initialize slpak for current day as assumed by cgwfread() called from cnguts.cpp each hour b4 this fcn.
419419
// Don't know a) if other parts of program depend on it (else do in wswfread each call)
420420
// b) if would be faster to push & pop the data it sets.
421-
slday( Top.jDayST, // julian date of simulation (standard time), cnguts.cpp. Use of ST matches call in cgwthr.cpp.
422-
SLTMLST ); // say use local standard time
421+
slday(Top.jDayST, // julian date of simulation (standard time), cnguts.cpp. Use of ST matches call in cgwthr.cpp.
422+
SLTMLST, // say use local standard time
423+
1); // skip if no day change
423424
// slpak.cpp: set up curr SLLOCDAT struct (which is cse.cpp:Locsolar) for given day:
424425
// sets info re declination of earth's axis, hourly sunupf[], dircos[], slazm[], etc.
425426
// Used by most other slpak calls.
@@ -873,7 +874,7 @@ void SgThruWin::tw_Doit()
873874

874875
// target gain for SGDISTs
875876

876-
for (sgi = 0; sgi < tw_xr->x.nsgdist; sgi++) // explicit user-entered targets
877+
for (int sgi = 0; sgi < tw_xr->x.nsgdist; sgi++) // explicit user-entered targets
877878
{
878879
SGDIST* sgd = tw_xr->x.sgdist + sgi; // point to sgdist
879880
if (sgd->sd_targTy == SGDTTSURFI || sgd->sd_targTy == SGDTTSURFO)

src/CGWTHR.CPP

Lines changed: 45 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,7 @@ RC TOPRAT::tp_WthrInit() // Initialize weather data/ display any error message
8484
RC TOPRAT::tp_WthrBegDay()
8585
{
8686
RC rc = RCOK;
87-
87+
rc = Wfile.wf_UpSampleDay(jDay);
8888

8989
return rc;
9090
} // TOPRAT::tp_WthrBegDay
@@ -267,6 +267,16 @@ o else { aes = 0.f; bes = 1.5f - g; ces = g - .5f; }
267267
radBeamShAv = (a * radBeamPvHrAv + b * radBeamHrAv + c * radBeamNxHrAv) * beamAdj;
268268
radDiffShAv = (a * radDiffPvHrAv + b * radDiffHrAv + c * radDiffNxHrAv) * diffAdj;
269269

270+
#if 0
271+
float radBeamX, radDiffX;
272+
Wfile.wf_GetSubhrSolar(iHr, iSubhr, radBeamX, radDiffX);
273+
if (frDiff(radBeamShAv, radBeamX) > .001f || frDiff(radDiffShAv, radDiffX) > .001f)
274+
{
275+
printf("\nSolar mismatch");
276+
Wfile.wf_UpSampleDay(jDay);
277+
}
278+
#endif
279+
270280
// Interpolate end-subhour instantaneous values for same data
271281

272282
#ifdef SOLAVNEND // undef in cndefns.h
@@ -404,31 +414,44 @@ RC WDHR::wd_WfReader( // read an hour's weather data and make adjustments
404414
rc = pWF->wf_Read( this, jDayST, iHrST, WRN|wfOp); // Read hour's data from weather file
405415
break;
406416
}
407-
if (rc) // if wfRead failed, eg date not in file or type without design days
408-
return rc;
409-
410-
// Optional anisotropic sky adjustment
411-
// Do NOT adjust wd_DNI, wd_DHI
412-
if (Top.skyModel==C_SKYMODCH_ANISO)
413-
slaniso( &wd_bmrad, &wd_dfrad, iHrST); // adjust data in place to approx model sky brighter
414-
// near sun, etc, while still computing with sun's
415-
// beam and isotropic diffuse radiation. slpak.cpp. */
417+
#if defined( SOLARFIX)
418+
float bmrad = wd_DNI;
419+
float dfrad = wd_DHI;
420+
if (Top.skyModel == C_SKYMODCH_ANISO)
421+
slaniso(&bmrad, &dfrad,iHrST);
422+
if (frDiff(bmrad, wd_bmrad) > .0001f
423+
|| frDiff(dfrad, wd_dfrad) > 0.0001f)
424+
printf("\nDiff");
425+
#else
426+
if (!rc) // if wfRead failed, eg date not in file or type without design days
427+
wd_Adjust(iHrST);
428+
#endif
416429

417-
// other adjustments
418-
wd_bmrad *= Top.radBeamF; // Adjust radiation values for possible user input factors, defaults 1.0.
419-
wd_dfrad *= Top.radDiffF; // ..
420-
wd_wndSpd = Top.windF * max( wd_wndSpd, Top.windSpeedMin);
421-
// apply wind speed min (user input, default = .5)
422-
// and adjust by factor (per user input, default .25)
430+
return rc;
431+
} // WDHR::wd_WfReader
432+
//-----------------------------------------------------------------------------
433+
void WDHR::wd_Adjust( // apply adjustments to weather data
434+
int iHrST) // standard time hour of day (0-23)
435+
{
423436

424-
// Ensure solar data values are not negative (as found in some CSW files)
425-
wd_bmrad = max(wd_bmrad, 0.f);
426-
wd_dfrad = max(wd_dfrad, 0.f);
427-
wd_glrad = max(wd_glrad, 0.f);
437+
// Optional anisotropic sky adjustment
438+
// Do NOT adjust wd_DNI, wd_DHI
439+
if (Top.skyModel == C_SKYMODCH_ANISO)
440+
slaniso(&wd_bmrad, &wd_dfrad, iHrST); // adjust data in place to approx model sky brighter
441+
// near sun, etc, while still computing with sun's
442+
// beam and isotropic diffuse radiation. slpak.cpp. */
428443

444+
// other solar adjustments
445+
// ensure solar data values are not negative (as found in some CSW files)
446+
wd_bmrad = max( Top.radBeamF*wd_bmrad, 0.f); // Adjust radiation values by possible user input factors, defaults 1.0.
447+
wd_dfrad = max( Top.radDiffF*wd_dfrad, 0.f); // ..
448+
wd_glrad = max(wd_glrad, 0.f); // TODO: re-derive from adjusted wd_bmrad and wd_dfrad?
429449

430-
return rc;
431-
} // WDHR::wd_WfReader
450+
wd_wndSpd = Top.windF * max(wd_wndSpd, Top.windSpeedMin);
451+
// apply wind speed min (user input, default = .5)
452+
// and adjust by factor (per user input, default .25)
453+
454+
} // WDHR::wd_Adjust
432455
//---------------------------------------------------------------------------
433456
void FC cgWfDone() // Close, clean up hourly simulator weather file
434457
{

src/CNDEFNS.H

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -132,9 +132,9 @@
132132
#define DIM_POLYGONXYZ 37 // input arrays dimension
133133
// = MAX_POLYLPVERTICIES*3 + 1
134134

135-
#undef SOLARFIX // define to correct timing of slday() calls
135+
#define SOLARFIX // define to correct timing of slday() calls
136136
// and definition of HA, 10-25-2017
137-
137+
// plus add'l changes, 8-2020
138138
#endif // ifndef _CNEDEFNS_H
139139

140140
// cndefns.h end

src/CNRECS.DEF

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -687,6 +687,8 @@ RECORD WFILE "weatherFile" *RAT // weather file info, one static instance "Wfile
687687
*declare "RC wf_EtDecodeHdr( char* hdr, int erOp, float* clrnss, float* turbid, float* atmois);"
688688
*declare "RC wf_DecodeHdrFields( char* hdr, struct WFHTAB* wfht0, int erOp);"
689689
*declare "RC wf_FillWDYEAR( int erOp=WRN);"
690+
*declare "RC wf_UpSampleDay( int jDay);"
691+
*declare "void wf_GetSubhrSolar( int iHr, int iSh, float& radBeam, float& radDiff) const;"
690692
*declare "RC wf_Read( WDHR* pWd, int jDay, int iHr, int erOp = WRN);"
691693
*declare "USI* wf_PackedHrRead( int jDay, int iHr, int erOp = WRN);"
692694
*declare "LI wf_PackedHrOffset( int jDay, int iHr, int erOp = WRN);"
@@ -766,6 +768,7 @@ RECORD WDHR "wfdata sub" *SUBSTRUCT // hourly data substructure for WFDATA
766768
*declare "void wd_Init( int options=0);"
767769
*declare "WDHR& Copy( const WDHR& wd, int options=0);"
768770
*declare "RC wd_WfReader( BOO nextHour, WFILE* pWF);"
771+
*declare "void wd_Adjust( int iHrST);"
769772
*declare "RC wd_Unpack( int iH, USI* pHour, int wFileFormat=ET1);"
770773
*declare "RC wd_EstimateMissingET1( int iHr);"
771774
*declare "float wd_CalcSkyTemp( int skyModelLW, int iHr);"

src/SLPAK.CPP

Lines changed: 28 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -352,10 +352,6 @@ void FC slday( // set up daily data in current SLLOCDAT
352352
if ((options & 1) && slloccur->doy == doy && slloccur->timetype == timetype)
353353
return; // already set for doy
354354

355-
#if 0 && defined(_DEBUG)
356-
printf("\nslday %d %d", doy, timetype);
357-
#endif
358-
359355
slloccur->doy = doy;
360356

361357
float dec;
@@ -746,35 +742,35 @@ void FC slaltazm(/* Calculate solar altitude and azimuth for hour */
746742
} /* slaltazm */
747743
//======================================================================
748744
void FC slaniso(/* Adjust beam and diffuse radiation values
749-
according to Hay anisotropic sky model */
750-
751-
float *pbeam, /* Pointer to beam value (Btu/sf): used/replaced. */
752-
float *pdiff, /* Pointer to diffuse value (Btu/sf): used/replaced.*/
753-
SI ihr) /* Hour of day (0 - 23, 0 = midnight to 1 AM).
754-
Meaning of hour (LST, solar time, etc.)
755-
depends on how SLLOCDAT was set up by slday(). */
756-
757-
/* must call slday() for day first (uses slloccur members) */
758-
759-
/* Adjusted values of beam and diffuse *REPLACE* the current values */
760-
761-
/* Story: Code assumes sky is modelled as istropic (uniform) hemisphere of
762-
sky radiation plus direct sun beam. But actually, sky is brighter
763-
near sun, near horizon, etc. Hay model approximates reality better
764-
with old code by increasing beam to approximate some of the extra sky
765-
brightness near sun. Rob per Chip, 12-89. */
766-
767-
/* Recoded 2-10-89 based on cp4sim equivalent function. Features --
768-
1. Doesn't bother unless there is a little beam
769-
2. Constrains fb to be .8 max. This prevents wild values from
770-
early morning observations.
771-
3. Derives fd (diffuse factor) from fb rather than from basic
772-
Hay formula, giving same result unless fb hit .8 limit. In all
773-
cases, total horiz is preserved */
745+
according to Hay anisotropic sky model */
746+
747+
float *pbeam, /* Pointer to beam value (Btu/sf): used/replaced. */
748+
float *pdiff, /* Pointer to diffuse value (Btu/sf): used/replaced.*/
749+
SI ihr) /* Hour of day (0 - 23, 0 = midnight to 1 AM).
750+
Meaning of hour (LST, solar time, etc.)
751+
depends on how SLLOCDAT was set up by slday(). */
752+
753+
/* must call slday() for day first (uses slloccur members) */
754+
755+
/* Adjusted values of beam and diffuse *REPLACE* the current values */
756+
757+
/* Story: Code assumes sky is modelled as istropic (uniform) hemisphere of
758+
sky radiation plus direct sun beam. But actually, sky is brighter
759+
near sun, near horizon, etc. Hay model approximates reality better
760+
with old code by increasing beam to approximate some of the extra sky
761+
brightness near sun. Rob per Chip, 12-89. */
762+
763+
/* Recoded 2-10-89 based on cp4sim equivalent function. Features --
764+
1. Doesn't bother unless there is a little beam
765+
2. Constrains fb to be .8 max. This prevents wild values from
766+
early morning observations.
767+
3. Derives fd (diffuse factor) from fb rather than from basic
768+
Hay formula, giving same result unless fb hit .8 limit. In all
769+
cases, total horiz is preserved */
774770
{
775-
SI pos1, pos2;
776-
SI ihx;
777-
float c1, c2, cosi, f, fb, fd;
771+
SI pos1, pos2;
772+
SI ihx;
773+
float c1, c2, cosi, f, fb, fd;
778774

779775
if (*pbeam > 5.f) /* if a little beam */
780776
{

src/WFPAK.CPP

Lines changed: 51 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
#include "ancrec.h" // record: base class for rccn.h classes
1313
#include "rccn.h" // TOPRAT WFILE WFDATA
1414
#include "psychro.h"
15+
#include "slpak.h"
1516

1617
#include "yacam.h" // class YACAM
1718
#include "tdpak.h"
@@ -445,8 +446,10 @@ struct WDSUBHRFACTORS // constant factors for weather data interpolation
445446
class WDSUBHR // derived subhourly weather data
446447
{
447448
public:
448-
float wsh_radBeam;
449-
float wsh_radDiff;
449+
void wsh_ClearSolar()
450+
{ wsh_radBeamAv = wsh_radDiffAv = 0; }
451+
float wsh_radBeamAv;
452+
float wsh_radDiffAv;
450453
}; // class WDSUBHR
451454
//----------------------------------------------------------------------------
452455
struct VHR // sort helper for wdy_Stats
@@ -501,18 +504,19 @@ public:
501504
float wdy_TaDbAvg( int jDay1, int jDay2);
502505
RC wdy_UpSampleSetup(int nSh);
503506
RC wdy_UpSampleDay(int jDay, int nSh);
504-
RC wdy_UpSampleHr(int jDay, int nSh);
507+
RC wdy_UpSampleHr(WDSUBHR wdsh[], int jDay, int iHr, int nSh);
505508
}; // class WDYEAR
506509
//-----------------------------------------------------------------------------
507510
WDYEAR::WDYEAR() // c'tor
508-
: wdy_wShF(NULL)
511+
: wdy_wShF(NULL), wdy_shDay(NULL)
509512
{
510513
wdy_Init();
511514
} // WDYEAR::WDYEAR
512515
//-----------------------------------------------------------------------------
513516
WDYEAR::~WDYEAR() // d'tor
514517
{
515518
delete[] wdy_wShF;
519+
delete[] wdy_shDay;
516520
} // WDYEAR::~WDYEAR
517521
//-----------------------------------------------------------------------------
518522
void WDYEAR::wdy_Init(
@@ -589,10 +593,18 @@ RC WDYEAR::wdy_Fill( // read weather data for entire file; compute averages etc.
589593
{ int monLen = monLens[ iMon] + (wdy_isLeap && iMon==2);
590594
for (iDay=0; iDay<monLen; iDay++)
591595
{ jDay++;
596+
#if 1
597+
slday(jDay, SLTMLST);
598+
#endif
592599
for (int iHr=0; iHr<24; iHr++)
593-
{ rc |= pWF->wf_Read( &wdy_Hr( jDay, iHr), jDay, iHr, erOp|WF_FORCEREAD);
600+
{ WDHR* pWd = &wdy_Hr(jDay, iHr);
601+
rc |= pWF->wf_Read( pWd, jDay, iHr, erOp|WF_FORCEREAD);
594602
if (rc)
595603
break;
604+
#if defined( SOLARFIX)
605+
pWd->wd_Adjust( iHr); // apply adjusments per user input
606+
// aniso, solar factors, wind factor
607+
#endif
596608
}
597609
if (rc)
598610
break;
@@ -790,6 +802,8 @@ RC WDYEAR::wdy_UpSampleSetup(
790802

791803
delete[] wdy_wShF;
792804
wdy_wShF = new WDSUBHRFACTORS[nSh];
805+
delete[] wdy_shDay;
806+
wdy_shDay = new WDSUBHR[ 24*nSh];
793807

794808
for (int iSh = 0; iSh < nSh; iSh++)
795809
wdy_wShF[iSh].wds_Setup(iSh, nSh);
@@ -798,18 +812,39 @@ RC WDYEAR::wdy_UpSampleSetup(
798812

799813
} // WDYEAR::wdy_UpSampleSetup
800814
//-----------------------------------------------------------------------------
815+
RC WFILE::wf_UpSampleDay(
816+
int jDay)
817+
{
818+
return wf_pWDY ? wf_pWDY->wdy_UpSampleDay(jDay, Top.nSubSteps)
819+
: RCBAD;
820+
} // WFILE::wf_UpSampleDay
821+
//-----------------------------------------------------------------------------
822+
void WFILE::wf_GetSubhrSolar(
823+
int iHr,
824+
int iSh,
825+
float& radBeam,
826+
float& radDiff) const
827+
{
828+
const WDSUBHR* pWDSH = wf_pWDY->wdy_shDay + iHr*Top.nSubSteps + iSh;
829+
radBeam = pWDSH->wsh_radBeamAv;
830+
radDiff = pWDSH->wsh_radDiffAv;
831+
}
832+
//-----------------------------------------------------------------------------
801833
RC WDYEAR::wdy_UpSampleDay(
802834
int jDay, // day of year (1-365/366)
803835
int nSh)
804836
{
805-
837+
RC rc = RCOK;
806838
for (int iHr = 0; iHr < 24; iHr++)
807839
{
840+
WDSUBHR* pWDSH = wdy_shDay + iHr * nSh;
841+
rc |= wdy_UpSampleHr(pWDSH, jDay, iHr, nSh);
808842
}
843+
return rc;
809844
} // WDYEAR::wdy_UpSampleDay
810845
//-----------------------------------------------------------------------------
811846
RC WDYEAR::wdy_UpSampleHr(
812-
XXX wdSh,
847+
WDSUBHR wdSh[], // returned: subhour values
813848
int jDay, // day of year (1-365/366)
814849
int iHr, // hour of day, 0-23
815850
int nSh) // # of subhrs per hour
@@ -827,8 +862,10 @@ RC WDYEAR::wdy_UpSampleHr(
827862
}
828863

829864
if (radBeam[1] < .1f && radDiff[1] < .1f)
830-
{ // substep 0
831-
continue;
865+
{
866+
for (int iSh = 0; iSh < nSh; iSh++)
867+
wdSh[iSh].wsh_ClearSolar();
868+
return rc;
832869
}
833870

834871
// Compute adjustment factors (constant over hour) to make subhour values add up to given hour value.
@@ -871,8 +908,9 @@ RC WDYEAR::wdy_UpSampleHr(
871908

872909
// Interpolate subhour average power values for data with average values in file.
873910
// Multiply by subhrDur for energy.
874-
wdSh[ iSh].radBeamAv = VIProd(radBeam, 3, wf[iSh].slrF) * beamAdj;
875-
wdSh[ iSh].radDiffAv = VIProd(radDiff, 3, wf[iSh].slrF) * diffAdj;
911+
const float* slrF = wdy_wShF[iSh].slrF;
912+
wdSh[ iSh].wsh_radBeamAv = VIProd( radBeam, 3, slrF) * beamAdj;
913+
wdSh[ iSh].wsh_radDiffAv = VIProd( radDiff, 3, slrF) * diffAdj;
876914

877915
}
878916

@@ -1278,7 +1316,7 @@ WFILE::WFILE( basAnc *b, TI i, SI noZ /*=0*/) // c'tor to help insure init is ca
12781316
} // WFILE::WFILE
12791317
//----------------------------------------------------------------------------
12801318
WFILE::WFILE() // default c'tor (insurance)
1281-
: record( NULL, 0, 1), yac( NULL), yacTDV( NULL)
1319+
: record( NULL, 0, 1), yac( NULL), yacTDV( NULL), wf_pWDY( NULL)
12821320
{ wf_Init();
12831321
} // WFILE::WFILE
12841322
//----------------------------------------------------------------------------
@@ -2665,7 +2703,7 @@ x printf( "mismatch\n");
26652703
return rc;
26662704
} // WDHR::wd_EPWReadHr
26672705
#undef _C
2668-
2706+
//-----------------------------------------------------------------------------
26692707
RC WFILE::wf_FixJday(DOY& jDay, int begDay)
26702708
{
26712709
if (jd1 > 0 // if weather file dates known

0 commit comments

Comments
 (0)