Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix Bugs in Emmel and Blocken Convection Algorithms #9129

Merged
merged 10 commits into from
Nov 2, 2021
Merged

Conversation

mitchute
Copy link
Collaborator

@mitchute mitchute commented Oct 13, 2021

Pull request overview

Emmel et al. Table 3 - Convection correlations for walls and roofs
Screen Shot 2021-10-13 at 10 19 18 AM

Blocken et al. Table 6 - Convection correlations for windward surfaces
Screen Shot 2021-10-13 at 10 19 04 AM

@mitchute mitchute added the Defect Includes code to repair a defect in EnergyPlus label Oct 13, 2021
@mitchute mitchute added this to the EnergyPlus 2022.1 milestone Oct 13, 2021
@mitchute mitchute requested a review from Myoldmopar October 13, 2021 02:32
@mitchute mitchute self-assigned this Oct 13, 2021
@mitchute mitchute marked this pull request as draft October 13, 2021 02:32
@mitchute mitchute removed the request for review from Myoldmopar October 13, 2021 02:32
@mitchute mitchute marked this pull request as ready for review October 13, 2021 19:21
Copy link
Collaborator Author

@mitchute mitchute left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ready for review.

Theta = state.dataEnvrn->WindDir - Surface(SurfNum).Azimuth - 90.0; // TODO double check theta
Theta = CalcWindSurfaceTheta(state.dataEnvrn->WindDir, Surface(SurfNum).Azimuth);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the same theta angle calculation that was suspect before. Replacing it with the new unit-tested function.

Theta = state.dataSurface->SurfOutWindDir(SurfNum) - Surface(SurfNum).Azimuth - 90.0; // TODO double check theta
Theta = CalcWindSurfaceTheta(state.dataEnvrn->WindDir, Surface(SurfNum).Azimuth);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same

Copy link
Contributor

@rraustad rraustad Oct 13, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This argument should be SurfOutWindDir?

Comment on lines 8761 to 8773
Real64 CalcWindSurfaceTheta(Real64 const WindDir, Real64 const SurfAzimuth)
{
// Computes the angle theta between the wind direction and the surface azimuth
// Should always be a value between 0-180 deg

Real64 theta = std::abs(WindDir - SurfAzimuth);
if (theta > 180) {
return abs(theta - 360);
} else {
return theta;
}
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

New function for calculating the angle theta between the wind direction and the surface azimuth.

@@ -8787,16 +8800,15 @@ Real64 CalcBlockenWindward(Real64 const WindAt10m,

Real64 Theta; // angle between wind and surface azimuth

Theta = WindDir - SurfAzimuth - 90.0; // TODO double check theta
if (Theta > 180.0) Theta -= 360.0;
Theta = CalcWindSurfaceTheta(WindDir, SurfAzimuth);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Update suspect theta calculation.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could have combined 8001-8003 as Real64 Theta = ...

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks. Fixed.

Comment on lines 8805 to 8811
if (Theta <= 11.25) {
Hf = 4.6 * std::pow(WindAt10m, 0.89);
} else if ((11.25 < Theta) && (Theta <= 33.75)) {
} else if (Theta <= 33.75) {
Hf = 5.0 * std::pow(WindAt10m, 0.8);
} else if ((33.75 < Theta) && (Theta <= 56.25)) {
} else if (Theta <= 56.25) {
Hf = 4.6 * std::pow(WindAt10m, 0.84);
} else if ((56.25 < Theta) && (Theta <= 100.0)) {
} else if (Theta <= 90.0) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A few things here:

  • Don't need multiple bounding checks on theta at each condition. It should successively fall through until it hits the right one.
  • This is a "windward" function, so an upper bound of 100 deg seems inappropriate. 90 deg should be the max a "windward" surface could see.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

upper bound, rounding, what if Theta comes out as 90.0000000001 ?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, that makes sense. So... 91? Back to 100?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

And YOU get a unit test! That's up to you, I guess 91 should be adequate but 100 should never hurt anything, unless you want to use 91 and assert on an else.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks. I backed it down to 100 deg. Who knows how often these things are actually used, but 100 isn't unreasonable.

Comment on lines 8852 to 8860
if (Theta <= 22.5) {
Hf = 5.15 * std::pow(WindAt10m, 0.81);
} else if ((22.5 < Theta) && (Theta <= 67.5)) {
} else if (Theta <= 67.5) {
Hf = 3.34 * std::pow(WindAt10m, 0.84);
} else if ((67.5 < Theta) && (Theta <= 112.5)) {
} else if (Theta <= 112.5) {
Hf = 4.78 * std::pow(WindAt10m, 0.71);
} else if ((112.5 < Theta) && (Theta <= 157.5)) {
} else if (Theta <= 157.5) {
Hf = 4.05 * std::pow(WindAt10m, 0.77);
} else if ((157.5 < Theta) && (Theta <= 180.0)) {
} else if (Theta <= 180.0) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove duplicative checks here.

@@ -8894,19 +8905,18 @@ Real64 CalcEmmelRoof(EnergyPlusData &state,

Real64 Theta; // angle between wind and surface azimuth

Theta = WindDir - LongAxisOutwardAzimuth - 90.0; // TODO double check theta
if (Theta > 180.0) Theta -= 360.0;
Theta = CalcWindSurfaceTheta(WindDir, LongAxisOutwardAzimuth);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Update suspect theta calculation here.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

8906-8908

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

Comment on lines 8901 to 8919
Hf = 5.15 * std::pow(WindAt10m, 0.81);
} else if ((22.5 < Theta) && (Theta <= 67.5)) {
Hf = 3.34 * std::pow(WindAt10m, 0.84);
} else if ((67.5 < Theta) && (Theta <= 112.5)) {
Hf = 4.78 * std::pow(WindAt10m, 0.71);
} else if ((112.5 < Theta) && (Theta <= 157.5)) {
Hf = 4.05 * std::pow(WindAt10m, 0.77);
} else if ((157.5 < Theta) && (Theta <= 180.0)) {
Hf = 3.54 * std::pow(WindAt10m, 0.76);
Hf = 5.11 * std::pow(WindAt10m, 0.78);
} else if (Theta <= 67.5) {
Hf = 4.60 * std::pow(WindAt10m, 0.79);
} else if (Theta <= 112.5) {
Hf = 3.67 * std::pow(WindAt10m, 0.85);
} else if (Theta <= 157.5) {
Hf = 4.60 * std::pow(WindAt10m, 0.79);
} else if (Theta <= 180.0) {
Hf = 5.11 * std::pow(WindAt10m, 0.78);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like a pasteo error. Based on the paper, these are the numbers for a vertical surface, not a roof surface.

@@ -8919,7 +8929,7 @@ Real64 CalcEmmelRoof(EnergyPlusData &state,
"CalcEmmelRoof: Convection model wind angle calculation suspect and high theta correlation",
state.dataConvectionCoefficient->CalcEmmelRoofErrorIDX);

Hf = 3.54 * std::pow(WindAt10m, 0.76);
Hf = 3.67 * std::pow(WindAt10m, 0.85);
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure it can even make it here, TBH. I updated this to pull from the roof correlation, but this probably needs to be double-checked (by me) and removed if it's inaccessible.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I updated the error handling in these functions and fixed the theta angle calculation so that it's always bounded between 0-180.

@@ -2630,3 +2631,178 @@ TEST_F(ConvectionCoefficientsFixture, TestSetAdaptiveConvectionAlgoCoefficient)
expected_curve = UtilityRoutines::FindItemInList("NUSSELTJURGESDUPCURVE", state->dataConvectionCoefficient->HcOutsideUserCurve);
ASSERT_EQ(algorithm_identifier, expected_curve);
}

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You get a unit test, and you get a unit test. Everybody gets a unit test.

@mitchute
Copy link
Collaborator Author

@rraustad Thanks for the reviews. I made a few updates based on your comments. Let me know if you have anything else.

@rraustad
Copy link
Contributor

Yeah, looks like 0 diffs here and a final review did not find anything that stands out. Good to go.

@Myoldmopar
Copy link
Member

Another one that looks fully ready. Thanks for all the review here @rraustad. I'll pull develop into this one as well for due diligence. Assuming it is clean, I'll get it in the queue.

@Myoldmopar
Copy link
Member

I pulled develop in locally, ran all the tests and everything passed. I ran regressions against develop so that I didn't have to wait on CI and it came out perfect, no diffs. Merging this, thanks @mitchute

@Myoldmopar Myoldmopar merged commit 739c93d into develop Nov 2, 2021
@Myoldmopar Myoldmopar deleted the emmel_conv branch November 2, 2021 16:29
yujiex pushed a commit that referenced this pull request Jan 27, 2022
Fix Bugs in Emmel and Blocken Convection Algorithms
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Defect Includes code to repair a defect in EnergyPlus
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Theta in Emmel Vertical Convection Coefficients Model is incorrectly determined
8 participants