From 0875601fe06b4a25df6ea621a026664ef19d3993 Mon Sep 17 00:00:00 2001 From: Alireza Adli Date: Mon, 22 Apr 2024 12:49:43 -0400 Subject: [PATCH] Finalize the workflow with removing dissmissive buildings --- basic_functions.py | 13 ++++++++++++- handle_mtl_ds_workflow.py | 11 ++++++----- scrub_layer_class.py | 9 ++++++++- scrub_mtl_class.py | 40 ++++++++++++++++++++++++++++++--------- 4 files changed, 57 insertions(+), 16 deletions(-) diff --git a/basic_functions.py b/basic_functions.py index b99c5bc..53d5158 100644 --- a/basic_functions.py +++ b/basic_functions.py @@ -30,4 +30,15 @@ def create_folders(directory, num_folders): folder_name = f"layer_{i}" folder_path = os.path.join(directory, folder_name) os.makedirs(folder_path) - print(f"Created folder: {folder_path}") \ No newline at end of file + print(f"Created folder: {folder_path}") + + +def create_output_folders(paths_dict, output_dir): + for path in paths_dict.keys(): + new_folder = path.lower().replace(' ', '_') + output_path = output_dir + '/' + new_folder + os.mkdir(output_path) + if path[-1] != 's': + paths_dict[path] = output_path + f'/{new_folder}.shp' + else: + paths_dict[path] = output_path \ No newline at end of file diff --git a/handle_mtl_ds_workflow.py b/handle_mtl_ds_workflow.py index daf4fb2..a1b2851 100644 --- a/handle_mtl_ds_workflow.py +++ b/handle_mtl_ds_workflow.py @@ -14,7 +14,7 @@ montreal_boundary = \ # Processing the NRCan layer includes fixing its geometries print('Processing the NRCan layer') -print(f'Data Count of the NRCan layer: {nrcan.data_count}') +print(nrcan) nrcan.create_spatial_index() nrcan.fix_geometries(output_paths['Fixed NRCan']) @@ -126,11 +126,12 @@ single_parts_layer = ScrubLayer( print(single_parts_layer) single_parts_layer.create_spatial_index() -# The process of instantiating a new layer -# (including print and create part) can be a method -# Also experiment importing input_paths_and_layers - # Add an area field single_parts_layer.add_field('Area') single_parts_layer.assign_area('Area') +dismissive_area = 15 +single_parts_layer.conditional_delete_record('Area', '<', dismissive_area) + +print(f'After removing buildings with less than {dismissive_area} squaremeter area:') +print(single_parts_layer) diff --git a/scrub_layer_class.py b/scrub_layer_class.py index 0120f01..852099b 100644 --- a/scrub_layer_class.py +++ b/scrub_layer_class.py @@ -1,6 +1,6 @@ from qgis.core import QgsApplication, QgsField, QgsProject, \ QgsProcessingFeedback, QgsVectorLayer, QgsVectorDataProvider, \ - QgsExpressionContext, QgsExpressionContextUtils, edit + QgsExpressionContext, QgsExpressionContextUtils, edit, QgsFeatureRequest from qgis.PyQt.QtCore import QVariant from qgis.analysis import QgsNativeAlgorithms from basic_functions import * @@ -152,6 +152,13 @@ class ScrubLayer: # Update layer fields self.layer.updateFields() + def conditional_delete_record(self, field_name, operator, condition): + request = QgsFeatureRequest().setFilterExpression( + f'{field_name} {operator} {str(condition)}') + with edit(self.layer): + for feature in self.layer.getFeatures(request): + self.layer.deleteFeature(feature.id()) + def add_field(self, new_field_name): functionalities = self.layer.dataProvider().capabilities() diff --git a/scrub_mtl_class.py b/scrub_mtl_class.py index 3513c6d..047971f 100644 --- a/scrub_mtl_class.py +++ b/scrub_mtl_class.py @@ -32,13 +32,13 @@ class ScrubMTL: } @staticmethod - def merge_layers(layers_path, mered_layer_path): + def merge_layers(layers_path, mergeded_layer_path): merging_layers = find_shp_files(layers_path) QgsApplication.processingRegistry().addProvider(QgsNativeAlgorithms()) params = {'LAYERS': merging_layers, 'CRS': None, - 'OUTPUT': mered_layer_path} + 'OUTPUT': mergeded_layer_path} processing.run("native:mergevectorlayers", params) @@ -92,19 +92,41 @@ class ScrubMTL: f'{self.property_assessment.data_count}') self.property_assessment.create_spatial_index() + # def the_cleaning_workflow(self): + # """It carries out all the steps to clean the dataset.""" + # # self.generate_output_paths() + # # self.process_nrcan() + # # self.process_geo_index() + # # self.process_property_assesment() + # # self.property_assessment.clip_by_multiple(120, + # # self.output_paths['Fixed NRCan'], + # # self.output_paths['Splitted NRCans'], + # # self.output_paths + # # ['Pairwise Clipped Property Assessment Partitions'] + # # ) + # self.property_assessment.\ + # clip_by_multiple(120, 'the path', + # self.output_paths['Splitted NRCans'], + # self.output_paths['Pairwise Clipped Property Assessment Partitions']) def the_cleaning_workflow(self): """It carries out all the steps to clean the dataset.""" # self.generate_output_paths() # self.process_nrcan() # self.process_geo_index() # self.process_property_assesment() - self.clip_with_several_overlays(self.input_paths['Property Assessment'], - 'Property Assessment', - self.output_paths['Fixed NRCan'], - 'Fixed NRCan', - 10, self.output_paths['Splitted NRCans'], - self.output_paths - ['Pairwise Clipped Property Assessment Partitions']) + # self.property_assessment.clip_by_multiple(120, + # self.output_paths['Fixed NRCan'], + # self.output_paths['Splitted NRCans'], + # self.output_paths + # ['Pairwise Clipped Property Assessment Partitions'] + # ) + prop_a = ScrubLayer(self.qgis_path, self.input_paths['Property Assessment'], + 'Property Aim') + + prop_a.\ + clip_by_multiple(120, 'the path', + self.output_paths['Splitted NRCans'], + self.output_paths['Pairwise Clipped Property Assessment Partitions']) def refine_heights(self): pass