diff --git a/hub/catalog_factories/construction/nrcan_catalog.py b/hub/catalog_factories/construction/nrcan_catalog.py index 0fe42d72..554ac7a0 100644 --- a/hub/catalog_factories/construction/nrcan_catalog.py +++ b/hub/catalog_factories/construction/nrcan_catalog.py @@ -116,7 +116,7 @@ class NrcanCatalog(Catalog): climate_zone = archetype['climate_zone'] construction_period = archetype['period_of_construction'] average_storey_height = archetype['average_storey_height'] - thermal_capacity = str(float(archetype['thermal_capacity']) * 1000) + thermal_capacity = float(archetype['thermal_capacity']) * 1000 extra_loses_due_to_thermal_bridges = archetype['extra_loses_due_thermal_bridges'] infiltration_rate_for_ventilation_system_off = archetype['infiltration_rate_for_ventilation_system_off'] infiltration_rate_for_ventilation_system_on = archetype['infiltration_rate_for_ventilation_system_on'] diff --git a/hub/catalog_factories/usage/nrcan_catalog.py b/hub/catalog_factories/usage/nrcan_catalog.py index 0f60dc68..8caf9d10 100644 --- a/hub/catalog_factories/usage/nrcan_catalog.py +++ b/hub/catalog_factories/usage/nrcan_catalog.py @@ -53,7 +53,7 @@ class NrcanCatalog(Catalog): def _load_schedules(self): usage = self._metadata['nrcan'] - url = f'{self._base_url}{usage["schedules_location"]}' + url = f'{self._base_url}{usage["schedules"]}' _schedule_types = [] with urllib.request.urlopen(url) as json_file: schedules_type = json.load(json_file) @@ -76,12 +76,40 @@ class NrcanCatalog(Catalog): def _load_archetypes(self): usages = [] name = self._metadata['nrcan'] - url = f'{self._base_url}{name["space_types_location"]}' - with urllib.request.urlopen(url) as json_file: + url_1 = f'{self._base_url}{name["space_types"]}' + url_2 = f'{self._base_url}{name["space_types_compliance"]}' + with urllib.request.urlopen(url_1) as json_file: space_types = json.load(json_file)['tables']['space_types']['table'] space_types = [st for st in space_types if st['space_type'] == 'WholeBuilding'] + with urllib.request.urlopen(url_2) as json_file: + space_types_compliance = json.load(json_file)['tables']['space_compliance']['table'] + space_types_compliance = [st for st in space_types_compliance if st['space_type'] == 'WholeBuilding'] + space_types_dictionary = {} + for space_type in space_types_compliance: + usage_type = space_type['building_type'] + # people/m2 + occupancy_density = space_type['occupancy_per_area_people_per_m2'] + # W/m2 + lighting_density = space_type['lighting_per_area_w_per_m2'] + # W/m2 + appliances_density = space_type['electric_equipment_per_area_w_per_m2'] + # peak flow in gallons/h/m2 + domestic_hot_water_peak_flow = space_type['service_water_heating_peak_flow_per_area'] \ + * cte.GALLONS_TO_QUBIC_METERS / cte.HOUR_TO_SECONDS + space_types_dictionary[usage_type] = {'occupancy_per_area': occupancy_density, + 'lighting_per_area': lighting_density, + 'electric_equipment_per_area': appliances_density, + 'service_water_heating_peak_flow_per_area': domestic_hot_water_peak_flow + } + for space_type in space_types: usage_type = space_type['building_type'] + space_type_compliance = space_types_dictionary[usage_type] + occupancy_density = space_type_compliance['occupancy_per_area'] + lighting_density = space_type_compliance['lighting_per_area'] + appliances_density = space_type_compliance['electric_equipment_per_area'] + domestic_hot_water_peak_flow = space_type_compliance['service_water_heating_peak_flow_per_area'] + occupancy_schedule_name = space_type['occupancy_schedule'] lighting_schedule_name = space_type['lighting_schedule'] appliance_schedule_name = space_type['electric_equipment_schedule'] @@ -99,35 +127,26 @@ class NrcanCatalog(Catalog): hvac_availability = self._get_schedules(hvac_schedule_name) domestic_hot_water_load_schedule = self._get_schedules(domestic_hot_water_schedule_name) - occupancy_density = space_type['occupancy_per_area'] - # ACH mechanical_air_change = space_type['ventilation_air_changes'] # cfm/ft2 to m3/m2.s ventilation_rate = space_type['ventilation_per_area'] / (cte.METERS_TO_FEET * cte.MINUTES_TO_SECONDS) if ventilation_rate == 0: # cfm/person to m3/m2.s - ventilation_rate = space_type['ventilation_per_person'] / occupancy_density\ - / (cte.METERS_TO_FEET * cte.MINUTES_TO_SECONDS) + ventilation_rate = space_type['ventilation_per_person'] / (cte.METERS_TO_FEET * cte.MINUTES_TO_SECONDS)\ + / occupancy_density - # W/sqft to W/m2 - lighting_density = space_type['lighting_per_area'] * cte.METERS_TO_FEET * cte.METERS_TO_FEET lighting_radiative_fraction = space_type['lighting_fraction_radiant'] lighting_convective_fraction = 0 if lighting_radiative_fraction is not None: lighting_convective_fraction = 1 - lighting_radiative_fraction lighting_latent_fraction = 0 - # W/sqft to W/m2 - appliances_density = space_type['electric_equipment_per_area'] * cte.METERS_TO_FEET * cte.METERS_TO_FEET appliances_radiative_fraction = space_type['electric_equipment_fraction_radiant'] appliances_latent_fraction = space_type['electric_equipment_fraction_latent'] appliances_convective_fraction = 0 if appliances_radiative_fraction is not None and appliances_latent_fraction is not None: appliances_convective_fraction = 1 - appliances_radiative_fraction - appliances_latent_fraction - # peak flow in gallons/h/ft2 - domestic_hot_water_peak_flow = space_type['service_water_heating_peak_flow_per_area'] \ - * cte.GALLONS_TO_QUBIC_METERS / cte.HOUR_TO_SECONDS * pow(cte.METERS_TO_FEET, 2) domestic_hot_water_service_temperature = space_type['service_water_heating_target_temperature'] occupancy = Occupancy(occupancy_density, diff --git a/hub/data/usage/nrcan.xml b/hub/data/usage/nrcan.xml index dfcbf90a..9fb644b0 100644 --- a/hub/data/usage/nrcan.xml +++ b/hub/data/usage/nrcan.xml @@ -1,5 +1,6 @@ - NECB2020/data/space_types.json - NECB2015/data/schedules.json + NECB2015/data/space_types.json + NECB2015/qaqc/qaqc_data/space_compliance_2015.json> + NECB2015/data/schedules.json \ No newline at end of file diff --git a/hub/exports/building_energy/insel/insel_monthly_energy_balance.py b/hub/exports/building_energy/insel/insel_monthly_energy_balance.py index 6a11f924..f517abba 100644 --- a/hub/exports/building_energy/insel/insel_monthly_energy_balance.py +++ b/hub/exports/building_energy/insel/insel_monthly_energy_balance.py @@ -70,10 +70,11 @@ class InselMonthlyEnergyBalance(Insel): for i in range(1, len(surfaces) + 1): inputs.append(f"{str(100 + i)}.1 % Radiation surface {str(i)}") + number_of_storeys = int(building.eave_height / building.average_storey_height) # BUILDING PARAMETERS - parameters = [f'{0.85 * building.volume} % BP(1) Heated Volume (m3)', + parameters = [f'{building.volume} % BP(1) Heated Volume (m3)', f'{building.average_storey_height} % BP(2) Average storey height (m)', - f'{building.storeys_above_ground} % BP(3) Number of storeys above ground', + f'{number_of_storeys} % BP(3) Number of storeys above ground', f'{building.attic_heated} % BP(4) Attic heating type (0=no room, 1=unheated, 2=heated)', f'{building.basement_heated} % BP(5) Cellar heating type (0=no room, 1=unheated, 2=heated, ' f'99=invalid)'] @@ -93,11 +94,11 @@ class InselMonthlyEnergyBalance(Insel): for i, usage in enumerate(internal_zone.usages): percentage_usage = usage.percentage - parameters.append(f'{float(internal_zone.area) * percentage_usage} % BP(11) #1 Area of zone {i + 1} (m2)') + parameters.append(f'{internal_zone.thermal_zones[0].total_floor_area * percentage_usage} ' + f'% BP(11) #1 Area of zone {i + 1} (m2)') total_internal_gain = 0 for ig in usage.internal_gains: - total_internal_gain += float(ig.average_internal_gain) * \ - (float(ig.convective_fraction) + float(ig.radiative_fraction)) + total_internal_gain += ig.average_internal_gain * (ig.convective_fraction + ig.radiative_fraction) parameters.append(f'{total_internal_gain} % BP(12) #2 Internal gains of zone {i + 1}') parameters.append(f'{usage.thermal_control.mean_heating_set_point} % BP(13) #3 Heating setpoint temperature ' f'zone {i + 1} (degree Celsius)') @@ -107,7 +108,9 @@ class InselMonthlyEnergyBalance(Insel): f'zone {i + 1} (degree Celsius)') parameters.append(f'{usage.hours_day} % BP(16) #6 Usage hours per day zone {i + 1}') parameters.append(f'{usage.days_year} % BP(17) #7 Usage days per year zone {i + 1}') - parameters.append(f'{usage.mechanical_air_change} % BP(18) #8 Minimum air change rate zone {i + 1} (ACH)') + + ventilation_infiltration = usage.mechanical_air_change + internal_zone.thermal_zones[0].infiltration_rate_system_off + parameters.append(f'{ventilation_infiltration} % BP(18) #8 Minimum air change rate zone {i + 1} (ACH)') parameters.append(f'{len(thermal_zone.thermal_boundaries)} % Number of surfaces = BP(11+8z) \n' f'% 1. Surface type (1=wall, 2=ground 3=roof, 4=flat roof)\n' @@ -123,17 +126,18 @@ class InselMonthlyEnergyBalance(Insel): for thermal_boundary in thermal_zone.thermal_boundaries: type_code = _CONSTRUCTION_CODE[thermal_boundary.type] - window_area = 0 - if thermal_boundary.window_ratio < 1: - window_area = thermal_boundary.opaque_area * thermal_boundary.window_ratio / (1 - thermal_boundary.window_ratio) + wall_area = thermal_boundary.opaque_area * (1 + thermal_boundary.window_ratio) + if thermal_boundary.type == cte.WALL: + wall_area = wall_area * (1 - thermal_boundary.parent_surface.percentage_shared) + window_area = wall_area * thermal_boundary.window_ratio parameters.append(type_code) if thermal_boundary.type != cte.GROUND: - parameters.append(thermal_boundary.opaque_area + window_area) + parameters.append(wall_area) parameters.append('0.0') else: parameters.append('0.0') - parameters.append(thermal_boundary.opaque_area + window_area) + parameters.append(wall_area) parameters.append(thermal_boundary.u_value) parameters.append(window_area) diff --git a/hub/imports/usage/comnet_usage_parameters.py b/hub/imports/usage/comnet_usage_parameters.py index 163bd3fe..584c5b6b 100644 --- a/hub/imports/usage/comnet_usage_parameters.py +++ b/hub/imports/usage/comnet_usage_parameters.py @@ -76,7 +76,7 @@ class ComnetUsageParameters: # usage.occupancy when writing usage.occupancy = archetype.occupancy. # Same happens for lighting and appliances. Therefore, this walk around has been done. usage.mechanical_air_change = archetype.ventilation_rate / volume_per_area \ - * cte.HOUR_TO_MINUTES * cte.MINUTES_TO_SECONDS + * cte.HOUR_TO_SECONDS _occupancy = Occupancy() _occupancy.occupancy_density = archetype.occupancy.occupancy_density _occupancy.sensible_radiative_internal_gain = archetype.occupancy.sensible_radiative_internal_gain @@ -106,11 +106,13 @@ class ComnetUsageParameters: _domestic_hot_water = DomesticHotWater() _domestic_hot_water.density = archetype.domestic_hot_water.density _domestic_hot_water.service_temperature = archetype.domestic_hot_water.service_temperature - cold_temperature = cold_water_temperature[cte.YEAR]['epw'] - peak_flow = 0 - if (archetype.domestic_hot_water.service_temperature - cold_temperature) > 0: - peak_flow = archetype.domestic_hot_water.density / cte.WATER_DENSITY / cte.WATER_HEAT_CAPACITY \ - / (archetype.domestic_hot_water.service_temperature - cold_temperature) + peak_flow = None + if len(cold_water_temperature) > 0: + cold_temperature = cold_water_temperature[cte.YEAR]['epw'] + peak_flow = 0 + if (archetype.domestic_hot_water.service_temperature - cold_temperature) > 0: + peak_flow = archetype.domestic_hot_water.density / cte.WATER_DENSITY / cte.WATER_HEAT_CAPACITY \ + / (archetype.domestic_hot_water.service_temperature - cold_temperature) _domestic_hot_water.peak_flow = peak_flow _domestic_hot_water.schedules = archetype.domestic_hot_water.schedules usage.domestic_hot_water = _domestic_hot_water diff --git a/hub/imports/usage/nrcan_usage_parameters.py b/hub/imports/usage/nrcan_usage_parameters.py index 67a5e380..2577a781 100644 --- a/hub/imports/usage/nrcan_usage_parameters.py +++ b/hub/imports/usage/nrcan_usage_parameters.py @@ -64,7 +64,7 @@ class NrcanUsageParameters: usage = Usage() usage.name = usage_name self._assign_values(usage, archetype_usage, volume_per_area, building.cold_water_temperature) - self._assign_comnet_extra_values(usage, comnet_archetype_usage) + self._assign_comnet_extra_values(usage, comnet_archetype_usage, archetype_usage.occupancy.occupancy_density) usage.percentage = 1 self._calculate_reduced_values_from_extended_library(usage, archetype_usage) @@ -83,8 +83,8 @@ class NrcanUsageParameters: if archetype.mechanical_air_change > 0: usage.mechanical_air_change = archetype.mechanical_air_change elif archetype.ventilation_rate > 0: - usage.mechanical_air_change = archetype.ventilation_rate / volume_per_area \ - * cte.HOUR_TO_MINUTES * cte.MINUTES_TO_SECONDS + print(volume_per_area) + usage.mechanical_air_change = archetype.ventilation_rate / volume_per_area * cte.HOUR_TO_SECONDS else: usage.mechanical_air_change = 0 _occupancy = Occupancy() @@ -116,18 +116,24 @@ class NrcanUsageParameters: _domestic_hot_water = DomesticHotWater() _domestic_hot_water.peak_flow = archetype.domestic_hot_water.peak_flow _domestic_hot_water.service_temperature = archetype.domestic_hot_water.service_temperature - cold_temperature = cold_water_temperature[cte.YEAR]['epw'] - _domestic_hot_water.density = archetype.domestic_hot_water.peak_flow * cte.WATER_DENSITY * cte.WATER_HEAT_CAPACITY \ - * (archetype.domestic_hot_water.service_temperature - cold_temperature) + density = None + if len(cold_water_temperature) > 0: + cold_temperature = cold_water_temperature[cte.YEAR]['epw'] + density = archetype.domestic_hot_water.peak_flow * cte.WATER_DENSITY * cte.WATER_HEAT_CAPACITY \ + * (archetype.domestic_hot_water.service_temperature - cold_temperature) + _domestic_hot_water.density = density _domestic_hot_water.schedules = archetype.domestic_hot_water.schedules usage.domestic_hot_water = _domestic_hot_water @staticmethod - def _assign_comnet_extra_values(usage, archetype): + def _assign_comnet_extra_values(usage, archetype, occupancy_density): _occupancy = usage.occupancy - _occupancy.sensible_radiative_internal_gain = archetype.occupancy.sensible_radiative_internal_gain - _occupancy.latent_internal_gain = archetype.occupancy.latent_internal_gain - _occupancy.sensible_convective_internal_gain = archetype.occupancy.sensible_convective_internal_gain + archetype_density = archetype.occupancy.occupancy_density + _occupancy.sensible_radiative_internal_gain = archetype.occupancy.sensible_radiative_internal_gain \ + * occupancy_density / archetype_density + _occupancy.latent_internal_gain = archetype.occupancy.latent_internal_gain * occupancy_density / archetype_density + _occupancy.sensible_convective_internal_gain = archetype.occupancy.sensible_convective_internal_gain \ + * occupancy_density / archetype_density @staticmethod def _calculate_reduced_values_from_extended_library(usage, archetype):