2020-06-09 14:07:47 -04:00
|
|
|
"""
|
|
|
|
UsBasePhysicParameters, model the us archetypes and material, used by UsNewYorkCityPhysicsParameters and
|
|
|
|
UsPhysicsParameters as base class
|
|
|
|
SPDX - License - Identifier: LGPL - 3.0 - or -later
|
|
|
|
Copyright © 2020 Project Author Guille Gutierrez guillermo.gutierrezmorote@concordia.ca
|
|
|
|
"""
|
2020-06-11 15:45:11 -04:00
|
|
|
from pathlib import Path
|
2020-06-16 10:34:17 -04:00
|
|
|
|
2020-05-18 13:25:08 -04:00
|
|
|
import xmltodict
|
2020-06-16 10:34:17 -04:00
|
|
|
|
2020-05-18 13:25:08 -04:00
|
|
|
from city_model_structure.layer import Layer
|
|
|
|
from city_model_structure.material import Material
|
|
|
|
from physics.physics_feeders.helpers.us_to_library_types import UsToLibraryTypes
|
|
|
|
|
|
|
|
|
|
|
|
class UsBasePhysicsParameters:
|
2020-06-11 15:45:11 -04:00
|
|
|
"""
|
|
|
|
UsBasePhysicsParameters class
|
|
|
|
"""
|
2020-06-26 10:06:43 -04:00
|
|
|
def __init__(self, climate_zone, buildings, function_to_type, base_path):
|
2020-05-18 13:25:08 -04:00
|
|
|
self._climate_zone = climate_zone
|
2020-06-26 10:06:43 -04:00
|
|
|
self._buildings = buildings
|
2020-05-18 13:25:08 -04:00
|
|
|
# load US Library
|
2020-06-04 12:47:48 -04:00
|
|
|
path = str(Path.cwd() / base_path / 'us_constructions.xml')
|
2020-05-18 13:25:08 -04:00
|
|
|
with open(path) as xml:
|
|
|
|
self._library = xmltodict.parse(xml.read(), force_list='layer')
|
|
|
|
|
|
|
|
# load US Archetypes
|
2020-06-04 12:47:48 -04:00
|
|
|
path = str(Path.cwd() / base_path / 'us_archetypes.xml')
|
2020-05-18 13:25:08 -04:00
|
|
|
with open(path) as xml:
|
|
|
|
self._archetypes = xmltodict.parse(xml.read(), force_list='layer')
|
2020-06-26 10:06:43 -04:00
|
|
|
for building in self._buildings:
|
|
|
|
|
|
|
|
building_type = function_to_type(building.function)
|
2020-05-18 13:25:08 -04:00
|
|
|
if building_type is None:
|
|
|
|
return
|
2020-06-11 15:45:11 -04:00
|
|
|
archetype = self._search_archetype(building_type,
|
2020-06-26 10:12:58 -04:00
|
|
|
UsToLibraryTypes.yoc_to_standard(building.year_of_construction),
|
2020-06-11 15:45:11 -04:00
|
|
|
self._climate_zone)
|
2020-06-11 16:55:52 -04:00
|
|
|
# ToDo: remove this in the future
|
2020-05-18 13:25:08 -04:00
|
|
|
# ToDo: Raise WrongArchetype if not all the surface types are defined for the given city_object
|
|
|
|
if archetype is None:
|
2020-06-23 14:48:01 -04:00
|
|
|
print('Building ', city_object.name, 'has unknown archetype')
|
|
|
|
print('type: ', building_type, UsToLibraryTypes.yoc_to_standard(city_object.year_of_construction),
|
2020-05-18 13:25:08 -04:00
|
|
|
self._climate_zone)
|
2020-06-23 14:48:01 -04:00
|
|
|
continue
|
2020-05-18 13:25:08 -04:00
|
|
|
|
2020-06-26 10:06:43 -04:00
|
|
|
building.average_storey_height = archetype['average_storey_height']['#text']
|
|
|
|
building.storeys_above_ground = archetype['number_of_storeys']['#text']
|
2020-05-18 13:25:08 -04:00
|
|
|
|
2020-06-26 10:06:43 -04:00
|
|
|
for thermal_zone in building.thermal_zones:
|
2020-05-18 13:25:08 -04:00
|
|
|
thermal_zone.effective_thermal_capacity = archetype['thermal_capacity']['#text']
|
|
|
|
thermal_zone.additional_thermal_bridge_u_value = archetype['extra_loses_due_to_thermal_bridges']['#text']
|
|
|
|
thermal_zone.indirectly_heated_area_ratio = archetype['indirect_heated_ratio']['#text']
|
|
|
|
thermal_zone.infiltration_rate_system_off = archetype['infiltration_rate_for_ventilation_system_off']['#text']
|
|
|
|
thermal_zone.infiltration_rate_system_on = archetype['infiltration_rate_for_ventilation_system_on']['#text']
|
|
|
|
for thermal_boundary in thermal_zone.bounded:
|
|
|
|
construction_type = UsToLibraryTypes.construction_types[thermal_boundary.type]
|
2020-06-11 15:45:11 -04:00
|
|
|
construction = UsBasePhysicsParameters._search_construction_in_archetype(archetype, construction_type)
|
2020-05-18 13:25:08 -04:00
|
|
|
construction_id = construction['@id']
|
2020-06-11 15:45:11 -04:00
|
|
|
c_lib = self._search_construction_type('construction', construction_id)
|
2020-05-18 13:25:08 -04:00
|
|
|
if 'outside_solar_absorptance' in c_lib:
|
|
|
|
thermal_boundary.outside_solar_absorptance = c_lib['outside_solar_absorptance']['#text']
|
|
|
|
thermal_boundary.outside_thermal_absorptance = c_lib['outside_thermal_absorptance']['#text']
|
|
|
|
thermal_boundary.outside_visible_absorptance = c_lib['outside_visible_absorptance']['#text']
|
|
|
|
thermal_boundary.window_ratio = construction['window_ratio']['#text']
|
|
|
|
thermal_boundary.layers = []
|
|
|
|
for current_layer in c_lib['layers']['layer']:
|
|
|
|
layer = Layer()
|
|
|
|
if 'thickness' in current_layer:
|
2020-06-10 11:08:38 -04:00
|
|
|
layer.thickness = current_layer['thickness']['#text']
|
2020-06-11 15:45:11 -04:00
|
|
|
material_lib = self._search_construction_type('material', current_layer['material'])
|
2020-05-18 13:25:08 -04:00
|
|
|
material = Material()
|
|
|
|
if 'conductivity' in material_lib:
|
2020-06-10 11:08:38 -04:00
|
|
|
material.conductivity = material_lib['conductivity']['#text']
|
|
|
|
material.specific_heat = material_lib['specific_heat']['#text']
|
|
|
|
material.density = material_lib['density']['#text']
|
2020-05-18 13:25:08 -04:00
|
|
|
material.solar_absorptance = material_lib['solar_absorptance']['#text']
|
|
|
|
material.thermal_absorptance = material_lib['thermal_absorptance']['#text']
|
|
|
|
material.visible_absorptance = material_lib['visible_absorptance']['#text']
|
|
|
|
material.no_mass = 'no_mass' in material_lib
|
|
|
|
if 'thermal_resistance' in material_lib:
|
2020-06-10 11:08:38 -04:00
|
|
|
material.thermal_resistance = material_lib['thermal_resistance']['#text']
|
2020-05-18 13:25:08 -04:00
|
|
|
layer.material = material
|
|
|
|
thermal_boundary.layers.append(layer)
|
|
|
|
for opening in thermal_boundary.thermal_openings:
|
|
|
|
if construction['window'] is None:
|
|
|
|
continue
|
2020-06-11 15:45:11 -04:00
|
|
|
w_lib = self._search_construction_type('window', construction['window'])
|
|
|
|
opening.conductivity = w_lib['conductivity']['#text']
|
2020-05-18 13:25:08 -04:00
|
|
|
opening.frame_ratio = w_lib['frame_ratio']['#text']
|
|
|
|
opening.g_value = w_lib['solar_transmittance_at_normal_incidence']['#text']
|
2020-06-10 11:08:38 -04:00
|
|
|
opening.thickness = w_lib['thickness']['#text']
|
2020-06-09 15:17:19 -04:00
|
|
|
opening.back_side_solar_transmittance_at_normal_incidence = \
|
|
|
|
w_lib['back_side_solar_transmittance_at_normal_incidence']['#text']
|
|
|
|
opening.front_side_solar_transmittance_at_normal_incidence = \
|
|
|
|
w_lib['front_side_solar_transmittance_at_normal_incidence']['#text']
|
2020-05-18 13:25:08 -04:00
|
|
|
|
2020-06-11 15:45:11 -04:00
|
|
|
def _search_archetype(self, building_type, standard, climate_zone):
|
2020-05-18 13:25:08 -04:00
|
|
|
for archetype in self._archetypes['archetypes']['archetype']:
|
|
|
|
a_yc = str(archetype['@reference_standard'])
|
|
|
|
a_bt = str(archetype['@building_type'])
|
|
|
|
a_cz = str(archetype['@climate_zone'])
|
|
|
|
if (a_yc == str(standard)) and (a_bt == str(building_type)) and (a_cz == str(climate_zone)):
|
|
|
|
return archetype
|
|
|
|
return None
|
|
|
|
|
2020-06-11 15:45:11 -04:00
|
|
|
def _search_construction_type(self, construction_type, construction_id):
|
2020-05-18 13:25:08 -04:00
|
|
|
for c_lib in self._library['library'][construction_type + 's'][construction_type]:
|
|
|
|
if construction_id == c_lib['@id']:
|
|
|
|
return c_lib
|
|
|
|
raise Exception('Archetype definition contains elements that does not exist in the library')
|
|
|
|
|
|
|
|
@staticmethod
|
2020-06-11 15:45:11 -04:00
|
|
|
def _search_construction_in_archetype(archetype, construction_type):
|
2020-05-18 13:25:08 -04:00
|
|
|
for construction in archetype['constructions']['construction']:
|
|
|
|
if construction['@type'] == construction_type:
|
|
|
|
return construction
|
|
|
|
raise Exception('Construction type not found')
|