Skip to content

Commit 71f294a

Browse files
authored
Merge pull request #2034 from Esri/jy-rvw-geom-ops
update markdown headings and change hyperlinks to relative
2 parents 82dbb69 + 1eabebe commit 71f294a

File tree

1 file changed

+49
-33
lines changed

1 file changed

+49
-33
lines changed

guide/15-working-with-geometries/part3_spatial_operations_on_geometries.ipynb

Lines changed: 49 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
"cell_type": "markdown",
1212
"metadata": {},
1313
"source": [
14-
"Previously, in <a href=\"part1_introduction_what_is_geometry.ipynb\">Part 1</a> of this guide series to the `arcgis.geometry` module, you have seen the introduction to the module and some foundational concepts. In <a href=\"part2_working_with_geometries.ipynb\">Part 2</a>, you learned how to create geometry objects, their properties, and how to work with one, including its interactions with map widgets. In this part, let's continue to explore spatial operations of geometry objects using two different usage patterns."
14+
"Previously, in [Part 1](../part1-introduction-what-is-geometry/) of this guide series to the `arcgis.geometry` module, you have seen the introduction to the module and some foundational concepts. In [Part 2](../part2-working-with-geometries/), you learned how to create geometry objects, their properties, and how to work with one, including its interactions with map widgets. In this part, let's continue to explore spatial operations of geometry objects using two different usage patterns."
1515
]
1616
},
1717
{
@@ -38,8 +38,8 @@
3838
"### Two patterns of applying spatial operations\n",
3939
"There are two ways of performing spatial operations \n",
4040
"\n",
41-
"- (a) `Object Oriented Programming (OOP)` pattern - here you create a geometry object first, then call methods off the geometry object, and \n",
42-
"- (b) calling functions from `arcgis.geometry.functions` directly without instantiating any geometry objects, e.g. the `from_geo_coordinate_string` or `to_geo_coordinate_string` methods, which take spatial data as input, analyze the data, then produce output data that is the derivative of the analysis performed on the input data.\n",
41+
"- `Object Oriented Programming (OOP)` pattern - here you create a geometry object first, then call methods off the geometry object, and \n",
42+
"- `Server-side Processing` - calling functions from `arcgis.geometry.functions` directly without instantiating any geometry objects, e.g. the `from_geo_coordinate_string` or `to_geo_coordinate_string` methods, which take spatial data as input, analyze the data, then produce output data that is the derivative of the analysis performed on the input data.\n",
4343
"\n",
4444
"The major difference between these two is that the **OOP pattern uses local geometry engines** such as `shapely` or `arcpy`, while calling **functions from `arcgis.geometry.functions` will use server-side geometry engine** by sending the geometries over to the [Geometry Service](https://developers.arcgis.com/rest/services-reference/geometry-service.htm) configured with your web GIS server. If your web GIS is ArcGIS Online, the latter pattern requires credits. Further, the latter pattern is not performant for larger datasets. Users are recommended to only use (b) if they do not have access to either of the local geometry engines. Further more, if you want to process geometries on the server, rather than applying (b), you can also publish the data as feature service and then run analyses using `arcgis.feature` module.\n",
4545
"\n",
@@ -50,7 +50,7 @@
5050
"cell_type": "markdown",
5151
"metadata": {},
5252
"source": [
53-
"### a. OOP Pattern - Uses local geometry engine\n",
53+
"## OOP Pattern - Uses local geometry engine\n",
5454
"\n",
5555
"Before demonstrating spatial operations, let us first import the necessary libraries, and create a GIS instance that connects to ArcGIS Online.\n",
5656
"\n",
@@ -90,7 +90,7 @@
9090
"cell_type": "markdown",
9191
"metadata": {},
9292
"source": [
93-
"#### a1. Union\n",
93+
"### Union\n",
9494
"\n",
9595
"The first method, `<first geom object>.union(<second_geometry>)`, can be called off from a geometry object to construct the geometry that is the set-theoretic union of the input geometries. You are going to see an example of how to create a union of two polygons (e.g. geometry1 and geometry2):"
9696
]
@@ -217,7 +217,7 @@
217217
"cell_type": "markdown",
218218
"metadata": {},
219219
"source": [
220-
"#### a2. Difference\n",
220+
"### Difference\n",
221221
"\n",
222222
"The, `difference(second_geometry)`, constructs the geometry that is composed only of the region unique to the base geometry but not part of the second geometry. The following illustration shows the results that are inside the source geometry, but not the second geometry."
223223
]
@@ -299,7 +299,7 @@
299299
"cell_type": "markdown",
300300
"metadata": {},
301301
"source": [
302-
"#### a3. Symmetric difference\n",
302+
"### Symmetric difference\n",
303303
"\n",
304304
"Similar to `difference()`, the method `symmetric_difference(second_geometry)` constructs the geometry that is the union of two geometries minus the intersection of those geometries. As told by the definition, the result of `difference()` should always be included/contained in the result of a `symmetric_difference()`."
305305
]
@@ -357,7 +357,7 @@
357357
"cell_type": "markdown",
358358
"metadata": {},
359359
"source": [
360-
"#### a4. intersect() V.S. overlaps()\n",
360+
"### intersect() V.S. overlaps()\n",
361361
"\n",
362362
"The `intersect()` method constructs a geometry that is the geometric intersection of the two input geometries. Different dimension values can be used to create different shape types. The intersection of two geometries of the same shape type is a geometry containing only the regions of overlap between the original geometries, and its arguments include:\n",
363363
" - `second_geometry`: required `arcgis.geometry.Geometry`. \n",
@@ -453,7 +453,7 @@
453453
"cell_type": "markdown",
454454
"metadata": {},
455455
"source": [
456-
"#### a5. Equals\n",
456+
"### Equals\n",
457457
"\n",
458458
"`equals()` compares the source geometry with the second to check if they are of the same shape type and define the same set of points in the plane. This is a `2D comparison` only; M and Z values are ignored."
459459
]
@@ -502,7 +502,7 @@
502502
"cell_type": "markdown",
503503
"metadata": {},
504504
"source": [
505-
"#### a6. generalize() V.S. buffer()\n",
505+
"### Generalize() V.S. buffer()\n",
506506
"\n",
507507
"Next, you will see the difference between these two spatial operations:\n",
508508
" - `generalize(max_offset)` - Creates a new simplified geometry using a specified maximum offset tolerance (as shown in Figs 1 and 2). The result of the `generalize()` operation against a polyline object is a new polyline, while that against a polygon object is a new polygon.\n",
@@ -807,7 +807,7 @@
807807
"cell_type": "markdown",
808808
"metadata": {},
809809
"source": [
810-
"#### a7. Find the nearest point\n",
810+
"### Find the nearest point\n",
811811
"\n",
812812
"Imagine that you are jogging on a trail (drawn as the light blue line segment on the map) inside Central Park and looking for a water fountain. You know the water fountain is located inside the pavilion (as marked as the blue pin). You want to know: What is the shortest path from the trail to pavilion?\n",
813813
"\n",
@@ -1007,7 +1007,7 @@
10071007
"cell_type": "markdown",
10081008
"metadata": {},
10091009
"source": [
1010-
"#### a8. contains()\n",
1010+
"### Contains\n",
10111011
"\n",
10121012
"The method `contains(second_geometry, relation=None)` indicates if the base geometry contains the comparison geometry."
10131013
]
@@ -1145,7 +1145,7 @@
11451145
"cell_type": "markdown",
11461146
"metadata": {},
11471147
"source": [
1148-
"#### a9. Clip a geometry object\n",
1148+
"### Clip a geometry object\n",
11491149
"\n",
11501150
"The method `clip(envelope)` constructs the intersection of the geometry and the specified extent. Note that, if `ArcPy` is not installed, none is returned. The one and required input parameter is:\n",
11511151
" - `envelope`: required tuple. The tuple must be in the form of a tuple (XMin, YMin, XMax, YMax) where each value represents the lower left bound and upper right bound of the extent."
@@ -1288,7 +1288,7 @@
12881288
"cell_type": "markdown",
12891289
"metadata": {},
12901290
"source": [
1291-
"### b. `arcgis.geometry.functions` pattern: using the server-side geometry engine\n",
1291+
"## Server-side geometry engine: Using `arcgis.geometry.functions`\n",
12921292
"\n",
12931293
"Besides calling methods off the geometry object as discussed in section (a), users can also call spatial operations directly from `arcgis.geometry.functions`. In the following section, you will see spatial operations such as `union` and `intersect` being performed with global functions."
12941294
]
@@ -1306,7 +1306,7 @@
13061306
"cell_type": "markdown",
13071307
"metadata": {},
13081308
"source": [
1309-
"#### b1. Union"
1309+
"### Union"
13101310
]
13111311
},
13121312
{
@@ -1415,7 +1415,7 @@
14151415
"cell_type": "markdown",
14161416
"metadata": {},
14171417
"source": [
1418-
"#### b2. intersect() V.S. overlaps()\n",
1418+
"### Intersect() V.S. overlaps()\n",
14191419
"\n",
14201420
"The intersect function `arcgis.geometry.functions.intersect(spatial_ref, geometries, geometry, gis=None)` is performed on a geometry service resource. This function constructs the set-theoretic intersection between an array of geometries and another geometry. The dimension of each resultant geometry is the minimum dimension of the input geometry in the geometries array and the other geometry specified by the geometry parameter. Inputs include:\n",
14211421
" - `spatial_ref` - The well-known ID or a spatial reference JSON object for the input geometries.\n",
@@ -1554,7 +1554,7 @@
15541554
"cell_type": "markdown",
15551555
"metadata": {},
15561556
"source": [
1557-
"#### b3. Difference\n",
1557+
"### Difference\n",
15581558
"\n",
15591559
"In order to construct the set-theoretic difference between each element of an array of geometries and another geometry (a.k.a. the so-called difference geometry), users need to perform a `difference` function on a geomtry service resource, which requires these inputs:\n",
15601560
" - `geometries` - An array of points, multipoints, polylines or polygons. The structure of each geometry in the array is the same as the structure of the JSON geometry objects returned by the ArcGIS REST API.\n",
@@ -1715,7 +1715,7 @@
17151715
"cell_type": "markdown",
17161716
"metadata": {},
17171717
"source": [
1718-
"#### b4. Symmetric difference\n",
1718+
"### Symmetric difference\n",
17191719
"\n",
17201720
"Again, there is no direct match of the aforementioned `symmetric_difference()` function in the `arcgis.geometry.functions`. In situations when the OOP pattern of this call is not applicable, you can construct your own customized function to create the geometry that is the union of two geometries minus the instersection of those geometries."
17211721
]
@@ -1833,7 +1833,7 @@
18331833
"cell_type": "markdown",
18341834
"metadata": {},
18351835
"source": [
1836-
"#### b5. Equals\n",
1836+
"### Equals\n",
18371837
"\n",
18381838
"There is no direct match of `equals()` function in the `arcgis.geometry.functions`. In situations when OOP pattern of this call is not applicable, you can construct your own customized function that checks if two geometries are equal."
18391839
]
@@ -1912,7 +1912,7 @@
19121912
"cell_type": "markdown",
19131913
"metadata": {},
19141914
"source": [
1915-
"#### b6. generalize() V.S. buffer()\n",
1915+
"### Generalize() V.S. buffer()\n",
19161916
"\n",
19171917
"In section (a6), we have already discussed the difference between these two spatial operations:\n",
19181918
" - `generalize(max_offset)` - Creates a new simplified geometry using a specified maximum offset tolerance.\n",
@@ -2544,7 +2544,7 @@
25442544
"cell_type": "markdown",
25452545
"metadata": {},
25462546
"source": [
2547-
"#### b7. Distance\n",
2547+
"### Distance\n",
25482548
"\n",
25492549
"From section (a7) we have figured out that `a_p` is the closest point on the trail from the pavilion, is there a way to confirm that the distance from `a_p` to the `access_point` is in fact the shortest?\n",
25502550
"\n",
@@ -2679,9 +2679,17 @@
26792679
"outputs": [],
26802680
"source": [
26812681
"map3.content.draw(access_point, \n",
2682-
" symbol = PictureMarkerSymbolEsriPMS(**{\"angle\":0,\"xoffset\":2,\"yoffset\":8,\"type\":\"esriPMS\",\n",
2683-
" \"url\":\"http://static.arcgis.com/images/Symbols/Basic/BlueShinyPin.png\",\n",
2684-
" \"contentType\":\"image/png\",\"width\":24,\"height\":24}))"
2682+
" symbol = PictureMarkerSymbolEsriPMS(**{\"angle\":0,\n",
2683+
" \"xoffset\":2,\n",
2684+
" \"yoffset\":8,\n",
2685+
" \"type\":\"esriPMS\",\n",
2686+
" \"url\":\"http://static.arcgis.com/images/Symbols/Basic/BlueShinyPin.png\",\n",
2687+
" \"contentType\":\"image/png\",\n",
2688+
" \"width\":24,\n",
2689+
" \"height\":24\n",
2690+
" }\n",
2691+
" )\n",
2692+
" )"
26852693
]
26862694
},
26872695
{
@@ -2691,9 +2699,17 @@
26912699
"outputs": [],
26922700
"source": [
26932701
"map3.content.draw(a_p, \n",
2694-
" symbol = PictureMarkerSymbolEsriPMS(**{\"angle\":0,\"xoffset\":2,\"yoffset\":8,\"type\":\"esriPMS\",\n",
2695-
" \"url\":\"http://static.arcgis.com/images/Symbols/Basic/GreenShinyPin.png\",\n",
2696-
" \"contentType\":\"image/png\",\"width\":24,\"height\":24}))"
2702+
" symbol = PictureMarkerSymbolEsriPMS(**{\"angle\":0,\n",
2703+
" \"xoffset\":2,\n",
2704+
" \"yoffset\":8,\n",
2705+
" \"type\":\"esriPMS\",\n",
2706+
" \"url\":\"http://static.arcgis.com/images/Symbols/Basic/GreenShinyPin.png\",\n",
2707+
" \"contentType\":\"image/png\",\n",
2708+
" \"width\":24,\n",
2709+
" \"height\":24\n",
2710+
" }\n",
2711+
" )\n",
2712+
" )"
26972713
]
26982714
},
26992715
{
@@ -2707,7 +2723,7 @@
27072723
"cell_type": "markdown",
27082724
"metadata": {},
27092725
"source": [
2710-
"#### b8. Determine the spatial relation between two geometries\n",
2726+
"### Determine the spatial relation between two geometries\n",
27112727
"\n",
27122728
"The relation function `arcgis.geometry.functions.relation(geometries1, geometries2, spatial_ref, spatial_relation='esriGeometryRelationIntersection', relation_param='', gis=None)` is performed on a geometry service resource. This function determines the pairs of geometries from the input geometry arrays that participate in the specified spatial relation. Both arrays are assumed to be in the spatial reference specified by `spatial_ref`, which is a required parameter. Geometry types cannot be mixed within an array. The relations are evaluated in 2D. In other words, z coordinates are not used.\n",
27132729
"\n",
@@ -3001,7 +3017,7 @@
30013017
"cell_type": "markdown",
30023018
"metadata": {},
30033019
"source": [
3004-
"#### b9. Clip a geometry object\n",
3020+
"### Clip a geometry object\n",
30053021
"\n",
30063022
"There is no direct match in the `arcgis.geometry.functions` that is equivalent to `clips()`, but we can take advantage of `intersect()` and write our own customized function that creates the `envelope` object to clip with, and performs `intersect()` with source geometry to generate the equivalent clipped result."
30073023
]
@@ -3132,7 +3148,7 @@
31323148
"cell_type": "markdown",
31333149
"metadata": {},
31343150
"source": [
3135-
"#### b10. Areas and Lengths\n",
3151+
"### Areas and Lengths\n",
31363152
"\n",
31373153
"The `areas_and_lengths` function calculates areas and perimeter lengths for each `Polygon` object specified in the input array. The input parameters include:\n",
31383154
" - `polygons` - The array of polygons whose areas and lengths are to be computed.\n",
@@ -3266,8 +3282,8 @@
32663282
"metadata": {},
32673283
"source": [
32683284
"In this notebook, we explored the two approaches to performing spatial operations: \n",
3269-
"- (a) Object Oriented Programming (OOP) pattern (calling operations directly off Geometry object). This pattern utilizes local geometry engines (ArcPy or Shapely) and performs the computation on the machine running the Python kernel \n",
3270-
"- (b) calling functions from `arcgis.geometry.functions`, which sends the spatial data over to a Geometry Service running on the active GIS connection, performs the operations remotely, and returns the results as Geometry objects.\n",
3285+
"- Object Oriented Programming (OOP) pattern (calling operations directly off Geometry object). This pattern utilizes local geometry engines (ArcPy or Shapely) and performs the computation on the machine running the Python kernel \n",
3286+
"- Server-side Processing by calling functions from `arcgis.geometry.functions`, which sends the spatial data over to a Geometry Service running on the active GIS connection, performs the operations remotely, and returns the results as Geometry objects.\n",
32713287
"\n",
32723288
"In most cases, approach (a) is simpler and more staightforward, and is recommended for users getting to use the ArcGIS API for Python. Additionally, another advantage of (a) is that it does not consume credits and is performant for larger datasets. However, (a) uses local geometry engines such as `shapely` or `arcpy`- in situations where neither shapely nor arcpy is installed on the execution environment, approach (b) is the alternative."
32733289
]
@@ -3289,7 +3305,7 @@
32893305
"name": "python",
32903306
"nbconvert_exporter": "python",
32913307
"pygments_lexer": "ipython3",
3292-
"version": "3.10.14"
3308+
"version": "3.11.0"
32933309
},
32943310
"toc": {
32953311
"base_numbering": 1,

0 commit comments

Comments
 (0)