basic implementation of pitched roof area estimate

This commit is contained in:
Khalim Conn-Kowlessar 2023-11-13 15:57:51 +09:00
parent 22a0bb1ffd
commit c96fafa701
4 changed files with 83 additions and 2 deletions

View file

@ -11,7 +11,9 @@ from utils.s3 import read_dataframe_from_s3_parquet
from epc_api.client import EpcClient
from BaseUtility import Definitions
from recommendations.rdsap_tables import england_wales_age_band_lookup
from recommendations.recommendation_utils import estimate_floors, estimate_perimeter, get_wall_type, estimate_wall_area
from recommendations.recommendation_utils import (
estimate_floors, estimate_perimeter, get_wall_type, estimate_wall_area, esimtate_pitched_roof_area
)
ENVIRONMENT = os.environ.get('ENVIRONMENT', 'dev')
EPC_AUTH_TOKEN = os.environ.get('EPC_AUTH_TOKEN')
@ -79,6 +81,7 @@ class Property(Definitions):
self.floor_height = None
self.insulation_wall_area = None
self.floor_area = None
self.pitched_roof_area = None
if epc_client:
self.epc_client = epc_client
@ -587,6 +590,10 @@ class Property(Definitions):
num_floors=self.number_of_floors, floor_height=self.floor_height, perimeter=self.perimeter
)
self.pitched_roof_area = esimtate_pitched_roof_area(
floor_area=self.floor_area / self.number_of_floors, floor_height=self.floor_height
)
def set_wall_type(self):
"""
This method sets the wall type of the property, using a simple approach based on the wall description

View file

@ -54,10 +54,13 @@ class RoofRecommendations:
u_value = get_roof_u_value(**{**self.property.roof, "age_band": self.property.age_band})
if self.property.roof["is_pitched"]:
# We recommend loft insulation
self.recommend_loft_insulation(u_value, insulation_thickness)
return
if self.property.roof["is_roof_room"]:
self.recommend_room_roof_insulation(u_value, insulation_thickness)
return
raise NotImplementedError("Implement me")
@staticmethod
@ -132,3 +135,21 @@ class RoofRecommendations:
)
self.recommendations = recommendations
def recommend_room_roof_insulation(self, u_value, insulation_thickness):
"""
This method recommends room in roof insulation for properties that have been identified
to possess a room in roof.
Because we currently have limited data about the construction of the roof, we make the following
assumptions:
1) The room in roof has a sloped roof.
We will make some basic estimations about the area of the roof given the floor area and the height of the
floors
2) Insulation of external walls is covered by the wall recommendation class
3) We assume a "Gable" roof type
:param u_value:
:param insulation_thickness:
:return:
"""

View file

@ -1,6 +1,7 @@
import math
from copy import deepcopy
import numpy as np
import pandas as pd
from recommendations.rdsap_tables import (
@ -594,3 +595,33 @@ def convert_thickness_to_numeric(string_thickness):
return int(string_thickness.replace("+", ""))
return int(string_thickness)
def esimtate_pitched_roof_area(floor_area: float, floor_height: float) -> float:
"""
This function will estimate the area of a pitched roof, given the floor area below the roof and the floor
height of the property.
Given limited information about the home, this is a very rough method to estimate the roof area and we
assume the the room is a gable roof.
We assume a roughly average pitch of 45 degrees
Note that both floor area and height should be in the same units. E.g. if floor area is meters squared,
floor height should be in meters
:param floor_area: area of the home's floor
:param floor_height: height of the home's floors
:return: Numerical estimate of the surface area of the top of the pitched roof
"""
# We estimate the length of the wall by just modelling the house as a square
wall_width = np.sqrt(floor_area)
# We're modelling the roof as two triangles where we know two of the three sides.
# The floor height makes up one side and half of the wall width makes up the other side
slope = np.sqrt(np.square(wall_width / 2) + np.square(floor_height))
area = 2 * (slope * wall_width)
return area

View file

@ -192,3 +192,25 @@ class TestRoofRecommendations:
roof_recommender6.recommend()
assert len(roof_recommender6.recommendations) == 0
def test_uninsulated_room_in_roof(self):
property_instance7 = Property(id=0, address1="fake", postcode="fake", epc_client=Mock())
property_instance7.age_band = "F"
property_instance7.floor_area = 100
property_instance7.roof = {
'original_description': 'Roof room(s), no insulation (assumed)',
'clean_description': 'Roof room(s), no insulation',
'thermal_transmittance': None, 'thermal_transmittance_unit': None, 'is_pitched': False,
'is_roof_room': True, 'is_loft': False, 'is_flat': False, 'is_thatched': False, 'is_at_rafters': False,
'is_assumed': True, 'has_dwelling_above': False, 'is_valid': True, 'insulation_thickness': 'none'
}
property_instance7
roof_recommender7 = RoofRecommendations(
property_instance=property_instance7, materials=loft_insulation_materials
)
assert not roof_recommender7.recommendations
roof_recommender7.recommend()