Polygons#

In addition to points, lines, areas, rasters, and trimeshes, Datashader can quickly render large collections of polygons (filled polylines). Datashader’s polygon support depends on data structures provided by the separate spatialpandas library, which extends Pandas and Parquet to support efficient storage and manipulation of “ragged” (variable length) data like polygons.

Before running these examples, you will need spatialpandas installed with pip:

$ pip install spatialpandas

or conda:

$ conda install -c pyviz spatialpandas
import pandas as pd
import numpy as np
import dask.dataframe as dd
import colorcet as cc
import datashader as ds
import datashader.transfer_functions as tf
import spatialpandas as sp
import spatialpandas.geometry
import spatialpandas.dask

Pandas supports custom column types using an “ExtensionArray” interface. Spatialpandas provides two Pandas ExtensionArrays that support polygons:

  • spatialpandas.geometry.PolygonArray: Each row in the column is a single Polygon instance. As with shapely and geopandas, each Polygon may contain zero or more holes.

  • spatialpandas.geometry.MultiPolygonArray: Each row in the column is a MultiPolygon instance, each of which can store one or more polygons, with each polygon containing zero or more holes.

Datashader assumes that the vertices of the outer filled polygon will be listed as x1, y1, x2, y2, etc. in counter clockwise (CCW) order around the polygon edge, while the holes will be in clockwise (CW) order. All polygons (both filled and holes) must be “closed”, with the first vertex of each polygon repeated as the last vertex.

Simple Example#

Here is a simple example of a two-element MultiPolygonArray. The first element specifies two filled polygons, the first with two holes. The second element contains one filled polygon with one hole.

polygons = sp.geometry.MultiPolygonArray([
    # First Element
    [[[0, 0, 1, 0, 2, 2, -1, 4, 0, 0],         # Filled quadrilateral (CCW order)
      [0.5, 1,  1, 2,  1.5, 1.5,  0.5, 1],     # Triangular hole (CW order)
      [0, 2, 0, 2.5, 0.5, 2.5, 0.5, 2, 0, 2]], # Rectangular hole (CW order)

     [[-0.5, 3, 1.5, 3, 1.5, 4, -0.5, 3]],],   # Filled triangle

    # Second Element
    [[[1.25, 0, 1.25, 2, 4, 2, 4, 0, 1.25, 0],          # Filled rectangle (CCW order)
      [1.5, 0.25, 3.75, 0.25, 3.75, 1.75, 1.5, 1.75, 1.5, 0.25]],]]) # Rectangular hole (CW order)

The filled quadrilateral starts at (x,y) (0,0) and goes to (1,0), then (2,2), then (-1,4), and back to (0,0); others similarly go left to right (but drawing in either CCW or CW order around the edge of the polygon depending on whether they are filled or holes).

Since a MultiPolygonArray is a pandas/dask extension array, it can be added as a column to a DataFrame. For convenience, you can define your DataFrame as sp.GeoDataFrame instead of pd.DataFrame, which will automatically include support for polygon columns:

df = sp.GeoDataFrame({'polygons': polygons, 'v': range(1, len(polygons)+1)})
df
polygons v
0 MultiPolygon([[[0.0, 0.0, 1.0, 0.0, 2.0, 2.0, ... 1
1 MultiPolygon([[[1.25, 0.0, 1.25, 2.0, 4.0, 2.0... 2

Polygons are rasterized to a Canvas by Datashader using the Canvas.polygons method. This method works like the existing glyph methods (.points, .line, etc), except it does not have x and y arguments. Instead, it has a single geometry argument that should be passed the name of a PolygonArray or MultiPolygonArray column in the supplied DataFrame. For comparison we’ll also show the polygon outlines rendered with Canvas.line (which also supports geometry columns):

%%time
cvs = ds.Canvas()
agg = cvs.polygons(df, geometry='polygons', agg=ds.sum('v'))
filled = tf.shade(agg)
float(agg.min()), float(agg.max())
CPU times: user 3.22 s, sys: 28.1 ms, total: 3.24 s
Wall time: 3.24 s
(1.0, 3.0)
%%time
cvs = ds.Canvas()
agg = cvs.line(df, geometry='polygons', agg=ds.sum('v'), line_width=4)
unfilled = tf.shade(agg)
float(agg.min()), float(agg.max())
CPU times: user 2.24 s, sys: 23.6 ms, total: 2.26 s
Wall time: 2.26 s
(0.0032808413085092525, 3.0)
tf.Images(filled, unfilled)




Here as you can see each polygon is filled or outlined with the indicated value from the v column for that polygon specification. The sum aggregator for the filled polygons specifies that the rendered colors should indicate the sum of the v values of polygons that overlap that pixel, and so the first element (v=1) has an overlapping area with value 2, and the second element has a value of 2 except in overlap areas where it gets a value of 3. Each plot is normalized separately, so the filled plot uses the colormap for the range 1 (light blue) to 3 (dark blue), while the outlined plot ranges from 1 to 2.

You can use polygons from within interactive plotting programs with axes to see the underlying values by hovering, which helps for comparing Datashader’s aggregation-based approach (right) to standard polygon rendering (left):

import holoviews as hv
from holoviews.operation.datashader import rasterize
from holoviews.streams import PlotSize
PlotSize.scale=2 # Sharper plots on Retina displays
hv.extension("bokeh")

hvpolys = hv.Polygons(df, vdims=['v']).opts(color='v', tools=['hover'])
hvpolys + rasterize(hvpolys, aggregator=ds.sum('v')).opts(tools=['hover'])

Realistic Example#

Here is a more realistic example, plotting the unemployment rate of the counties in Texas.

import bokeh.sampledata
try:
    from bokeh.sampledata.us_counties import data # noqa
except:
    bokeh.sampledata.download()
from bokeh.sampledata.us_counties  import data as counties
from bokeh.sampledata.unemployment import data as unemployment

counties = { code: county for code, county in counties.items()
            if county["state"] in ["tx"] }

county_boundaries = [[[*zip(county["lons"] + county["lons"][:1],
                            county["lats"] + county["lats"][:1])]
                     for county in counties.values()]]

county_rates = [unemployment[county_id] for county_id in counties]

boundary_coords = [[np.concatenate(list(
    zip(county["lons"][::-1] + county["lons"][-1:],
        county["lats"][::-1] + county["lats"][-1:])
))] for county in counties.values()]

boundaries = sp.geometry.PolygonArray(boundary_coords)

county_info = sp.GeoDataFrame({'boundary': boundaries,
                               'unemployment': county_rates})
Creating /home/runner/.bokeh directory
Creating /home/runner/.bokeh/data directory
Using data directory: /home/runner/.bokeh/data
Fetching 'CGM.csv'
Downloading: CGM.csv (1589982 bytes)

 16384     [  1.03%%]
 32768     [  2.06%%]
 49152     [  3.09%%]
 65536     [  4.12%%]
 81920     [  5.15%%]
 98304     [  6.18%%]
 114688    [  7.21%%]
 131072    [  8.24%%]
 147456    [  9.27%%]
 163840    [ 10.30%%]
 180224    [ 11.33%%]
 196608    [ 12.37%%]
 212992    [ 13.40%%]
 229376    [ 14.43%%]
 245760    [ 15.46%%]
 262144    [ 16.49%%]
 278528    [ 17.52%%]
 294912    [ 18.55%%]
 311296    [ 19.58%%]
 327680    [ 20.61%%]
 344064    [ 21.64%%]
 360448    [ 22.67%%]
 376832    [ 23.70%%]
 393216    [ 24.73%%]
 409600    [ 25.76%%]
 425984    [ 26.79%%]
 442368    [ 27.82%%]
 458752    [ 28.85%%]
 475136    [ 29.88%%]
 491520    [ 30.91%%]
 507904    [ 31.94%%]
 524288    [ 32.97%%]
 540672    [ 34.00%%]
 557056    [ 35.04%%]
 573440    [ 36.07%%]
 589824    [ 37.10%%]
 606208    [ 38.13%%]
 622592    [ 39.16%%]
 638976    [ 40.19%%]
 655360    [ 41.22%%]
 671744    [ 42.25%%]
 688128    [ 43.28%%]
 704512    [ 44.31%%]
 720896    [ 45.34%%]
 737280    [ 46.37%%]
 753664    [ 47.40%%]
 770048    [ 48.43%%]
 786432    [ 49.46%%]
 802816    [ 50.49%%]
 819200    [ 51.52%%]
 835584    [ 52.55%%]
 851968    [ 53.58%%]
 868352    [ 54.61%%]
 884736    [ 55.64%%]
 901120    [ 56.67%%]
 917504    [ 57.71%%]
 933888    [ 58.74%%]
 950272    [ 59.77%%]
 966656    [ 60.80%%]
 983040    [ 61.83%%]
 999424    [ 62.86%%]
 1015808   [ 63.89%%]
 1032192   [ 64.92%%]
 1048576   [ 65.95%%]
 1064960   [ 66.98%%]
 1081344   [ 68.01%%]
 1097728   [ 69.04%%]
 1114112   [ 70.07%%]
 1130496   [ 71.10%%]
 1146880   [ 72.13%%]
 1163264   [ 73.16%%]
 1179648   [ 74.19%%]
 1196032   [ 75.22%%]
 1212416   [ 76.25%%]
 1228800   [ 77.28%%]
 1245184   [ 78.31%%]
 1261568   [ 79.34%%]
 1277952   [ 80.38%%]
 1294336   [ 81.41%%]
 1310720   [ 82.44%%]
 1327104   [ 83.47%%]
 1343488   [ 84.50%%]
 1359872   [ 85.53%%]
 1376256   [ 86.56%%]
 1392640   [ 87.59%%]
 1409024   [ 88.62%%]
 1425408   [ 89.65%%]
 1441792   [ 90.68%%]
 1458176   [ 91.71%%]
 1474560   [ 92.74%%]
 1490944   [ 93.77%%]
 1507328   [ 94.80%%]
 1523712   [ 95.83%%]
 1540096   [ 96.86%%]
 1556480   [ 97.89%%]
 1572864   [ 98.92%%]
 1589248   [ 99.95%%]
 1589982   [100.00%%]
Fetching 'US_Counties.zip'
Downloading: US_Counties.zip (3171836 bytes)

 16384     [  0.52%%]
 32768     [  1.03%%]
 49152     [  1.55%%]
 65536     [  2.07%%]
 81920     [  2.58%%]
 98304     [  3.10%%]
 114688    [  3.62%%]
 131072    [  4.13%%]
 147456    [  4.65%%]
 163840    [  5.17%%]
 180224    [  5.68%%]
 196608    [  6.20%%]
 212992    [  6.72%%]
 229376    [  7.23%%]
 245760    [  7.75%%]
 262144    [  8.26%%]
 278528    [  8.78%%]
 294912    [  9.30%%]
 311296    [  9.81%%]
 327680    [ 10.33%%]
 344064    [ 10.85%%]
 360448    [ 11.36%%]
 376832    [ 11.88%%]
 393216    [ 12.40%%]
 409600    [ 12.91%%]
 425984    [ 13.43%%]
 442368    [ 13.95%%]
 458752    [ 14.46%%]
 475136    [ 14.98%%]
 491520    [ 15.50%%]
 507904    [ 16.01%%]
 524288    [ 16.53%%]
 540672    [ 17.05%%]
 557056    [ 17.56%%]
 573440    [ 18.08%%]
 589824    [ 18.60%%]
 606208    [ 19.11%%]
 622592    [ 19.63%%]
 638976    [ 20.15%%]
 655360    [ 20.66%%]
 671744    [ 21.18%%]
 688128    [ 21.69%%]
 704512    [ 22.21%%]
 720896    [ 22.73%%]
 737280    [ 23.24%%]
 753664    [ 23.76%%]
 770048    [ 24.28%%]
 786432    [ 24.79%%]
 802816    [ 25.31%%]
 819200    [ 25.83%%]
 835584    [ 26.34%%]
 851968    [ 26.86%%]
 868352    [ 27.38%%]
 884736    [ 27.89%%]
 901120    [ 28.41%%]
 917504    [ 28.93%%]
 933888    [ 29.44%%]
 950272    [ 29.96%%]
 966656    [ 30.48%%]
 983040    [ 30.99%%]
 999424    [ 31.51%%]
 1015808   [ 32.03%%]
 1032192   [ 32.54%%]
 1048576   [ 33.06%%]
 1064960   [ 33.58%%]
 1081344   [ 34.09%%]
 1097728   [ 34.61%%]
 1114112   [ 35.13%%]
 1130496   [ 35.64%%]
 1146880   [ 36.16%%]
 1163264   [ 36.67%%]
 1179648   [ 37.19%%]
 1196032   [ 37.71%%]
 1212416   [ 38.22%%]
 1228800   [ 38.74%%]
 1245184   [ 39.26%%]
 1261568   [ 39.77%%]
 1277952   [ 40.29%%]
 1294336   [ 40.81%%]
 1310720   [ 41.32%%]
 1327104   [ 41.84%%]
 1343488   [ 42.36%%]
 1359872   [ 42.87%%]
 1376256   [ 43.39%%]
 1392640   [ 43.91%%]
 1409024   [ 44.42%%]
 1425408   [ 44.94%%]
 1441792   [ 45.46%%]
 1458176   [ 45.97%%]
 1474560   [ 46.49%%]
 1490944   [ 47.01%%]
 1507328   [ 47.52%%]
 1523712   [ 48.04%%]
 1540096   [ 48.56%%]
 1556480   [ 49.07%%]
 1572864   [ 49.59%%]
 1589248   [ 50.10%%]
 1605632   [ 50.62%%]
 1622016   [ 51.14%%]
 1638400   [ 51.65%%]
 1654784   [ 52.17%%]
 1671168   [ 52.69%%]
 1687552   [ 53.20%%]
 1703936   [ 53.72%%]
 1720320   [ 54.24%%]
 1736704   [ 54.75%%]
 1753088   [ 55.27%%]
 1769472   [ 55.79%%]
 1785856   [ 56.30%%]
 1802240   [ 56.82%%]
 1818624   [ 57.34%%]
 1835008   [ 57.85%%]
 1851392   [ 58.37%%]
 1867776   [ 58.89%%]
 1884160   [ 59.40%%]
 1900544   [ 59.92%%]
 1916928   [ 60.44%%]
 1933312   [ 60.95%%]
 1949696   [ 61.47%%]
 1966080   [ 61.99%%]
 1982464   [ 62.50%%]
 1998848   [ 63.02%%]
 2015232   [ 63.54%%]
 2031616   [ 64.05%%]
 2048000   [ 64.57%%]
 2064384   [ 65.08%%]
 2080768   [ 65.60%%]
 2097152   [ 66.12%%]
 2113536   [ 66.63%%]
 2129920   [ 67.15%%]
 2146304   [ 67.67%%]
 2162688   [ 68.18%%]
 2179072   [ 68.70%%]
 2195456   [ 69.22%%]
 2211840   [ 69.73%%]
 2228224   [ 70.25%%]
 2244608   [ 70.77%%]
 2260992   [ 71.28%%]
 2277376   [ 71.80%%]
 2293760   [ 72.32%%]
 2310144   [ 72.83%%]
 2326528   [ 73.35%%]
 2342912   [ 73.87%%]
 2359296   [ 74.38%%]
 2375680   [ 74.90%%]
 2392064   [ 75.42%%]
 2408448   [ 75.93%%]
 2424832   [ 76.45%%]
 2441216   [ 76.97%%]
 2457600   [ 77.48%%]
 2473984   [ 78.00%%]
 2490368   [ 78.52%%]
 2506752   [ 79.03%%]
 2523136   [ 79.55%%]
 2539520   [ 80.06%%]
 2555904   [ 80.58%%]
 2572288   [ 81.10%%]
 2588672   [ 81.61%%]
 2605056   [ 82.13%%]
 2621440   [ 82.65%%]
 2637824   [ 83.16%%]
 2654208   [ 83.68%%]
 2670592   [ 84.20%%]
 2686976   [ 84.71%%]
 2703360   [ 85.23%%]
 2719744   [ 85.75%%]
 2736128   [ 86.26%%]
 2752512   [ 86.78%%]
 2768896   [ 87.30%%]
 2785280   [ 87.81%%]
 2801664   [ 88.33%%]
 2818048   [ 88.85%%]
 2834432   [ 89.36%%]
 2850816   [ 89.88%%]
 2867200   [ 90.40%%]
 2883584   [ 90.91%%]
 2899968   [ 91.43%%]
 2916352   [ 91.95%%]
 2932736   [ 92.46%%]
 2949120   [ 92.98%%]
 2965504   [ 93.49%%]
 2981888   [ 94.01%%]
 2998272   [ 94.53%%]
 3014656   [ 95.04%%]
 3031040   [ 95.56%%]
 3047424   [ 96.08%%]
 3063808   [ 96.59%%]
 3080192   [ 97.11%%]
 3096576   [ 97.63%%]
 3112960   [ 98.14%%]
 3129344   [ 98.66%%]
 3145728   [ 99.18%%]
 3162112   [ 99.69%%]
 3171836   [100.00%%]
Unpacking: US_Counties.csv
Fetching 'us_cities.json'
Downloading: us_cities.json (713565 bytes)
 16384     [  2.30%%]
 32768     [  4.59%%]
 49152     [  6.89%%]
 65536     [  9.18%%]
 81920     [ 11.48%%]
 98304     [ 13.78%%]
 114688    [ 16.07%%]
 131072    [ 18.37%%]
 147456    [ 20.66%%]
 163840    [ 22.96%%]
 180224    [ 25.26%%]
 196608    [ 27.55%%]
 212992    [ 29.85%%]
 229376    [ 32.15%%]
 245760    [ 34.44%%]
 262144    [ 36.74%%]
 278528    [ 39.03%%]
 294912    [ 41.33%%]
 311296    [ 43.63%%]
 327680    [ 45.92%%]
 344064    [ 48.22%%]
 360448    [ 50.51%%]
 376832    [ 52.81%%]
 393216    [ 55.11%%]
 409600    [ 57.40%%]
 425984    [ 59.70%%]
 442368    [ 61.99%%]
 458752    [ 64.29%%]
 475136    [ 66.59%%]
 491520    [ 68.88%%]
 507904    [ 71.18%%]
 524288    [ 73.47%%]
 540672    [ 75.77%%]
 557056    [ 78.07%%]
 573440    [ 80.36%%]
 589824    [ 82.66%%]
 606208    [ 84.95%%]
 622592    [ 87.25%%]
 638976    [ 89.55%%]
 655360    [ 91.84%%]
 671744    [ 94.14%%]
 688128    [ 96.44%%]
 704512    [ 98.73%%]
 713565    [100.00%%]
Fetching 'unemployment09.csv'
Downloading: unemployment09.csv (253301 bytes)
 16384     [  6.47%%]
 32768     [ 12.94%%]
 49152     [ 19.40%%]
 65536     [ 25.87%%]
 81920     [ 32.34%%]
 98304     [ 38.81%%]
 114688    [ 45.28%%]
 131072    [ 51.75%%]
 147456    [ 58.21%%]
 163840    [ 64.68%%]
 180224    [ 71.15%%]
 196608    [ 77.62%%]
 212992    [ 84.09%%]
 229376    [ 90.55%%]
 245760    [ 97.02%%]
 253301    [100.00%%]
Fetching 'AAPL.csv'
Downloading: AAPL.csv (166698 bytes)

 16384     [  9.83%%]
 32768     [ 19.66%%]
 49152     [ 29.49%%]
 65536     [ 39.31%%]
 81920     [ 49.14%%]
 98304     [ 58.97%%]
 114688    [ 68.80%%]
 131072    [ 78.63%%]
 147456    [ 88.46%%]
 163840    [ 98.29%%]
 166698    [100.00%%]
Fetching 'FB.csv'
Downloading: FB.csv (9706 bytes)
 9706      [100.00%%]

Fetching 'GOOG.csv'
Downloading: GOOG.csv (113894 bytes)
 16384     [ 14.39%%]
 32768     [ 28.77%%]
 49152     [ 43.16%%]
 65536     [ 57.54%%]
 81920     [ 71.93%%]
 98304     [ 86.31%%]
 113894    [100.00%%]
Fetching 'IBM.csv'
Downloading: IBM.csv (165625 bytes)

 16384     [  9.89%%]
 32768     [ 19.78%%]
 49152     [ 29.68%%]
 65536     [ 39.57%%]
 81920     [ 49.46%%]
 98304     [ 59.35%%]
 114688    [ 69.25%%]
 131072    [ 79.14%%]
 147456    [ 89.03%%]
 163840    [ 98.92%%]
 165625    [100.00%%]
Fetching 'MSFT.csv'
Downloading: MSFT.csv (161614 bytes)

 16384     [ 10.14%%]
 32768     [ 20.28%%]
 49152     [ 30.41%%]
 65536     [ 40.55%%]
 81920     [ 50.69%%]
 98304     [ 60.83%%]
 114688    [ 70.96%%]
 131072    [ 81.10%%]
 147456    [ 91.24%%]
 161614    [100.00%%]
Fetching 'WPP2012_SA_DB03_POPULATION_QUINQUENNIAL.zip'
Downloading: WPP2012_SA_DB03_POPULATION_QUINQUENNIAL.zip (4816256 bytes)
 16384     [  0.34%%]
 32768     [  0.68%%]
 49152     [  1.02%%]
 65536     [  1.36%%]
 81920     [  1.70%%]
 98304     [  2.04%%]
 114688    [  2.38%%]
 131072    [  2.72%%]
 147456    [  3.06%%]
 163840    [  3.40%%]
 180224    [  3.74%%]
 196608    [  4.08%%]
 212992    [  4.42%%]
 229376    [  4.76%%]
 245760    [  5.10%%]
 262144    [  5.44%%]
 278528    [  5.78%%]
 294912    [  6.12%%]
 311296    [  6.46%%]
 327680    [  6.80%%]
 344064    [  7.14%%]
 360448    [  7.48%%]
 376832    [  7.82%%]
 393216    [  8.16%%]
 409600    [  8.50%%]
 425984    [  8.84%%]
 442368    [  9.18%%]
 458752    [  9.53%%]
 475136    [  9.87%%]
 491520    [ 10.21%%]
 507904    [ 10.55%%]
 524288    [ 10.89%%]
 540672    [ 11.23%%]
 557056    [ 11.57%%]
 573440    [ 11.91%%]
 589824    [ 12.25%%]
 606208    [ 12.59%%]
 622592    [ 12.93%%]
 638976    [ 13.27%%]
 655360    [ 13.61%%]
 671744    [ 13.95%%]
 688128    [ 14.29%%]
 704512    [ 14.63%%]
 720896    [ 14.97%%]
 737280    [ 15.31%%]
 753664    [ 15.65%%]
 770048    [ 15.99%%]
 786432    [ 16.33%%]
 802816    [ 16.67%%]
 819200    [ 17.01%%]
 835584    [ 17.35%%]
 851968    [ 17.69%%]
 868352    [ 18.03%%]
 884736    [ 18.37%%]
 901120    [ 18.71%%]
 917504    [ 19.05%%]
 933888    [ 19.39%%]
 950272    [ 19.73%%]
 966656    [ 20.07%%]
 983040    [ 20.41%%]
 999424    [ 20.75%%]
 1015808   [ 21.09%%]
 1032192   [ 21.43%%]
 1048576   [ 21.77%%]
 1064960   [ 22.11%%]
 1081344   [ 22.45%%]
 1097728   [ 22.79%%]
 1114112   [ 23.13%%]
 1130496   [ 23.47%%]
 1146880   [ 23.81%%]
 1163264   [ 24.15%%]
 1179648   [ 24.49%%]
 1196032   [ 24.83%%]
 1212416   [ 25.17%%]
 1228800   [ 25.51%%]
 1245184   [ 25.85%%]
 1261568   [ 26.19%%]
 1277952   [ 26.53%%]
 1294336   [ 26.87%%]
 1310720   [ 27.21%%]
 1327104   [ 27.55%%]
 1343488   [ 27.89%%]
 1359872   [ 28.24%%]
 1376256   [ 28.58%%]
 1392640   [ 28.92%%]
 1409024   [ 29.26%%]
 1425408   [ 29.60%%]
 1441792   [ 29.94%%]
 1458176   [ 30.28%%]
 1474560   [ 30.62%%]
 1490944   [ 30.96%%]
 1507328   [ 31.30%%]
 1523712   [ 31.64%%]
 1540096   [ 31.98%%]
 1556480   [ 32.32%%]
 1572864   [ 32.66%%]
 1589248   [ 33.00%%]
 1605632   [ 33.34%%]
 1622016   [ 33.68%%]
 1638400   [ 34.02%%]
 1654784   [ 34.36%%]
 1671168   [ 34.70%%]
 1687552   [ 35.04%%]
 1703936   [ 35.38%%]
 1720320   [ 35.72%%]
 1736704   [ 36.06%%]
 1753088   [ 36.40%%]
 1769472   [ 36.74%%]
 1785856   [ 37.08%%]
 1802240   [ 37.42%%]
 1818624   [ 37.76%%]
 1835008   [ 38.10%%]
 1851392   [ 38.44%%]
 1867776   [ 38.78%%]
 1884160   [ 39.12%%]
 1900544   [ 39.46%%]
 1916928   [ 39.80%%]
 1933312   [ 40.14%%]
 1949696   [ 40.48%%]
 1966080   [ 40.82%%]
 1982464   [ 41.16%%]
 1998848   [ 41.50%%]
 2015232   [ 41.84%%]
 2031616   [ 42.18%%]
 2048000   [ 42.52%%]
 2064384   [ 42.86%%]
 2080768   [ 43.20%%]
 2097152   [ 43.54%%]
 2113536   [ 43.88%%]
 2129920   [ 44.22%%]
 2146304   [ 44.56%%]
 2162688   [ 44.90%%]
 2179072   [ 45.24%%]
 2195456   [ 45.58%%]
 2211840   [ 45.92%%]
 2228224   [ 46.26%%]
 2244608   [ 46.60%%]
 2260992   [ 46.95%%]
 2277376   [ 47.29%%]
 2293760   [ 47.63%%]
 2310144   [ 47.97%%]
 2326528   [ 48.31%%]
 2342912   [ 48.65%%]
 2359296   [ 48.99%%]
 2375680   [ 49.33%%]
 2392064   [ 49.67%%]
 2408448   [ 50.01%%]
 2424832   [ 50.35%%]
 2441216   [ 50.69%%]
 2457600   [ 51.03%%]
 2473984   [ 51.37%%]
 2490368   [ 51.71%%]
 2506752   [ 52.05%%]
 2523136   [ 52.39%%]
 2539520   [ 52.73%%]
 2555904   [ 53.07%%]
 2572288   [ 53.41%%]
 2588672   [ 53.75%%]
 2605056   [ 54.09%%]
 2621440   [ 54.43%%]
 2637824   [ 54.77%%]
 2654208   [ 55.11%%]
 2670592   [ 55.45%%]
 2686976   [ 55.79%%]
 2703360   [ 56.13%%]
 2719744   [ 56.47%%]
 2736128   [ 56.81%%]
 2752512   [ 57.15%%]
 2768896   [ 57.49%%]
 2785280   [ 57.83%%]
 2801664   [ 58.17%%]
 2818048   [ 58.51%%]
 2834432   [ 58.85%%]
 2850816   [ 59.19%%]
 2867200   [ 59.53%%]
 2883584   [ 59.87%%]
 2899968   [ 60.21%%]
 2916352   [ 60.55%%]
 2932736   [ 60.89%%]
 2949120   [ 61.23%%]
 2965504   [ 61.57%%]
 2981888   [ 61.91%%]
 2998272   [ 62.25%%]
 3014656   [ 62.59%%]
 3031040   [ 62.93%%]
 3047424   [ 63.27%%]
 3063808   [ 63.61%%]
 3080192   [ 63.95%%]
 3096576   [ 64.29%%]
 3112960   [ 64.63%%]
 3129344   [ 64.97%%]
 3145728   [ 65.31%%]
 3162112   [ 65.65%%]
 3178496   [ 66.00%%]
 3194880   [ 66.34%%]
 3211264   [ 66.68%%]
 3227648   [ 67.02%%]
 3244032   [ 67.36%%]
 3260416   [ 67.70%%]
 3276800   [ 68.04%%]
 3293184   [ 68.38%%]
 3309568   [ 68.72%%]
 3325952   [ 69.06%%]
 3342336   [ 69.40%%]
 3358720   [ 69.74%%]
 3375104   [ 70.08%%]
 3391488   [ 70.42%%]
 3407872   [ 70.76%%]
 3424256   [ 71.10%%]
 3440640   [ 71.44%%]
 3457024   [ 71.78%%]
 3473408   [ 72.12%%]
 3489792   [ 72.46%%]
 3506176   [ 72.80%%]
 3522560   [ 73.14%%]
 3538944   [ 73.48%%]
 3555328   [ 73.82%%]
 3571712   [ 74.16%%]
 3588096   [ 74.50%%]
 3604480   [ 74.84%%]
 3620864   [ 75.18%%]
 3637248   [ 75.52%%]
 3653632   [ 75.86%%]
 3670016   [ 76.20%%]
 3686400   [ 76.54%%]
 3702784   [ 76.88%%]
 3719168   [ 77.22%%]
 3735552   [ 77.56%%]
 3751936   [ 77.90%%]
 3768320   [ 78.24%%]
 3784704   [ 78.58%%]
 3801088   [ 78.92%%]
 3817472   [ 79.26%%]
 3833856   [ 79.60%%]
 3850240   [ 79.94%%]
 3866624   [ 80.28%%]
 3883008   [ 80.62%%]
 3899392   [ 80.96%%]
 3915776   [ 81.30%%]
 3932160   [ 81.64%%]
 3948544   [ 81.98%%]
 3964928   [ 82.32%%]
 3981312   [ 82.66%%]
 3997696   [ 83.00%%]
 4014080   [ 83.34%%]
 4030464   [ 83.68%%]
 4046848   [ 84.02%%]
 4063232   [ 84.36%%]
 4079616   [ 84.71%%]
 4096000   [ 85.05%%]
 4112384   [ 85.39%%]
 4128768   [ 85.73%%]
 4145152   [ 86.07%%]
 4161536   [ 86.41%%]
 4177920   [ 86.75%%]
 4194304   [ 87.09%%]
 4210688   [ 87.43%%]
 4227072   [ 87.77%%]
 4243456   [ 88.11%%]
 4259840   [ 88.45%%]
 4276224   [ 88.79%%]
 4292608   [ 89.13%%]
 4308992   [ 89.47%%]
 4325376   [ 89.81%%]
 4341760   [ 90.15%%]
 4358144   [ 90.49%%]
 4374528   [ 90.83%%]
 4390912   [ 91.17%%]
 4407296   [ 91.51%%]
 4423680   [ 91.85%%]
 4440064   [ 92.19%%]
 4456448   [ 92.53%%]
 4472832   [ 92.87%%]
 4489216   [ 93.21%%]
 4505600   [ 93.55%%]
 4521984   [ 93.89%%]
 4538368   [ 94.23%%]
 4554752   [ 94.57%%]
 4571136   [ 94.91%%]
 4587520   [ 95.25%%]
 4603904   [ 95.59%%]
 4620288   [ 95.93%%]
 4636672   [ 96.27%%]
 4653056   [ 96.61%%]
 4669440   [ 96.95%%]
 4685824   [ 97.29%%]
 4702208   [ 97.63%%]
 4718592   [ 97.97%%]
 4734976   [ 98.31%%]
 4751360   [ 98.65%%]
 4767744   [ 98.99%%]
 4784128   [ 99.33%%]
 4800512   [ 99.67%%]
 4816256   [100.00%%]
Unpacking: WPP2012_SA_DB03_POPULATION_QUINQUENNIAL.csv
Fetching 'gapminder_fertility.csv'
Downloading: gapminder_fertility.csv (64346 bytes)
 16384     [ 25.46%%]
 32768     [ 50.92%%]
 49152     [ 76.39%%]
 64346     [100.00%%]
Fetching 'gapminder_population.csv'
Downloading: gapminder_population.csv (94509 bytes)

 16384     [ 17.34%%]
 32768     [ 34.67%%]
 49152     [ 52.01%%]
 65536     [ 69.34%%]
 81920     [ 86.68%%]
 94509     [100.00%%]
Fetching 'gapminder_life_expectancy.csv'
Downloading: gapminder_life_expectancy.csv (73243 bytes)
 16384     [ 22.37%%]
 32768     [ 44.74%%]
 49152     [ 67.11%%]
 65536     [ 89.48%%]
 73243     [100.00%%]
Fetching 'gapminder_regions.csv'
Downloading: gapminder_regions.csv (7781 bytes)

 7781      [100.00%%]
Fetching 'world_cities.zip'
Downloading: world_cities.zip (645274 bytes)

 16384     [  2.54%%]
 32768     [  5.08%%]
 49152     [  7.62%%]
 65536     [ 10.16%%]
 81920     [ 12.70%%]
 98304     [ 15.23%%]
 114688    [ 17.77%%]
 131072    [ 20.31%%]
 147456    [ 22.85%%]
 163840    [ 25.39%%]
 180224    [ 27.93%%]
 196608    [ 30.47%%]
 212992    [ 33.01%%]
 229376    [ 35.55%%]
 245760    [ 38.09%%]
 262144    [ 40.63%%]
 278528    [ 43.16%%]
 294912    [ 45.70%%]
 311296    [ 48.24%%]
 327680    [ 50.78%%]
 344064    [ 53.32%%]
 360448    [ 55.86%%]
 376832    [ 58.40%%]
 393216    [ 60.94%%]
 409600    [ 63.48%%]
 425984    [ 66.02%%]
 442368    [ 68.56%%]
 458752    [ 71.09%%]
 475136    [ 73.63%%]
 491520    [ 76.17%%]
 507904    [ 78.71%%]
 524288    [ 81.25%%]
 540672    [ 83.79%%]
 557056    [ 86.33%%]
 573440    [ 88.87%%]
 589824    [ 91.41%%]
 606208    [ 93.95%%]
 622592    [ 96.48%%]
 638976    [ 99.02%%]
 645274    [100.00%%]
Unpacking: world_cities.csv
Fetching 'airports.json'
Downloading: airports.json (6373 bytes)

 6373      [100.00%%]
Fetching 'movies.db.zip'
Downloading: movies.db.zip (5053420 bytes)

 16384     [  0.32%%]
 32768     [  0.65%%]
 49152     [  0.97%%]
 65536     [  1.30%%]
 81920     [  1.62%%]
 98304     [  1.95%%]
 114688    [  2.27%%]
 131072    [  2.59%%]
 147456    [  2.92%%]
 163840    [  3.24%%]
 180224    [  3.57%%]
 196608    [  3.89%%]
 212992    [  4.21%%]
 229376    [  4.54%%]
 245760    [  4.86%%]
 262144    [  5.19%%]
 278528    [  5.51%%]
 294912    [  5.84%%]
 311296    [  6.16%%]
 327680    [  6.48%%]
 344064    [  6.81%%]
 360448    [  7.13%%]
 376832    [  7.46%%]
 393216    [  7.78%%]
 409600    [  8.11%%]
 425984    [  8.43%%]
 442368    [  8.75%%]
 458752    [  9.08%%]
 475136    [  9.40%%]
 491520    [  9.73%%]
 507904    [ 10.05%%]
 524288    [ 10.37%%]
 540672    [ 10.70%%]
 557056    [ 11.02%%]
 573440    [ 11.35%%]
 589824    [ 11.67%%]
 606208    [ 12.00%%]
 622592    [ 12.32%%]
 638976    [ 12.64%%]
 655360    [ 12.97%%]
 671744    [ 13.29%%]
 688128    [ 13.62%%]
 704512    [ 13.94%%]
 720896    [ 14.27%%]
 737280    [ 14.59%%]
 753664    [ 14.91%%]
 770048    [ 15.24%%]
 786432    [ 15.56%%]
 802816    [ 15.89%%]
 819200    [ 16.21%%]
 835584    [ 16.54%%]
 851968    [ 16.86%%]
 868352    [ 17.18%%]
 884736    [ 17.51%%]
 901120    [ 17.83%%]
 917504    [ 18.16%%]
 933888    [ 18.48%%]
 950272    [ 18.80%%]
 966656    [ 19.13%%]
 983040    [ 19.45%%]
 999424    [ 19.78%%]
 1015808   [ 20.10%%]
 1032192   [ 20.43%%]
 1048576   [ 20.75%%]
 1064960   [ 21.07%%]
 1081344   [ 21.40%%]
 1097728   [ 21.72%%]
 1114112   [ 22.05%%]
 1130496   [ 22.37%%]
 1146880   [ 22.70%%]
 1163264   [ 23.02%%]
 1179648   [ 23.34%%]
 1196032   [ 23.67%%]
 1212416   [ 23.99%%]
 1228800   [ 24.32%%]
 1245184   [ 24.64%%]
 1261568   [ 24.96%%]
 1277952   [ 25.29%%]
 1294336   [ 25.61%%]
 1310720   [ 25.94%%]
 1327104   [ 26.26%%]
 1343488   [ 26.59%%]
 1359872   [ 26.91%%]
 1376256   [ 27.23%%]
 1392640   [ 27.56%%]
 1409024   [ 27.88%%]
 1425408   [ 28.21%%]
 1441792   [ 28.53%%]
 1458176   [ 28.86%%]
 1474560   [ 29.18%%]
 1490944   [ 29.50%%]
 1507328   [ 29.83%%]
 1523712   [ 30.15%%]
 1540096   [ 30.48%%]
 1556480   [ 30.80%%]
 1572864   [ 31.12%%]
 1589248   [ 31.45%%]
 1605632   [ 31.77%%]
 1622016   [ 32.10%%]
 1638400   [ 32.42%%]
 1654784   [ 32.75%%]
 1671168   [ 33.07%%]
 1687552   [ 33.39%%]
 1703936   [ 33.72%%]
 1720320   [ 34.04%%]
 1736704   [ 34.37%%]
 1753088   [ 34.69%%]
 1769472   [ 35.02%%]
 1785856   [ 35.34%%]
 1802240   [ 35.66%%]
 1818624   [ 35.99%%]
 1835008   [ 36.31%%]
 1851392   [ 36.64%%]
 1867776   [ 36.96%%]
 1884160   [ 37.28%%]
 1900544   [ 37.61%%]
 1916928   [ 37.93%%]
 1933312   [ 38.26%%]
 1949696   [ 38.58%%]
 1966080   [ 38.91%%]
 1982464   [ 39.23%%]
 1998848   [ 39.55%%]
 2015232   [ 39.88%%]
 2031616   [ 40.20%%]
 2048000   [ 40.53%%]
 2064384   [ 40.85%%]
 2080768   [ 41.18%%]
 2097152   [ 41.50%%]
 2113536   [ 41.82%%]
 2129920   [ 42.15%%]
 2146304   [ 42.47%%]
 2162688   [ 42.80%%]
 2179072   [ 43.12%%]
 2195456   [ 43.44%%]
 2211840   [ 43.77%%]
 2228224   [ 44.09%%]
 2244608   [ 44.42%%]
 2260992   [ 44.74%%]
 2277376   [ 45.07%%]
 2293760   [ 45.39%%]
 2310144   [ 45.71%%]
 2326528   [ 46.04%%]
 2342912   [ 46.36%%]
 2359296   [ 46.69%%]
 2375680   [ 47.01%%]
 2392064   [ 47.34%%]
 2408448   [ 47.66%%]
 2424832   [ 47.98%%]
 2441216   [ 48.31%%]
 2457600   [ 48.63%%]
 2473984   [ 48.96%%]
 2490368   [ 49.28%%]
 2506752   [ 49.61%%]
 2523136   [ 49.93%%]
 2539520   [ 50.25%%]
 2555904   [ 50.58%%]
 2572288   [ 50.90%%]
 2588672   [ 51.23%%]
 2605056   [ 51.55%%]
 2621440   [ 51.87%%]
 2637824   [ 52.20%%]
 2654208   [ 52.52%%]
 2670592   [ 52.85%%]
 2686976   [ 53.17%%]
 2703360   [ 53.50%%]
 2719744   [ 53.82%%]
 2736128   [ 54.14%%]
 2752512   [ 54.47%%]
 2768896   [ 54.79%%]
 2785280   [ 55.12%%]
 2801664   [ 55.44%%]
 2818048   [ 55.77%%]
 2834432   [ 56.09%%]
 2850816   [ 56.41%%]
 2867200   [ 56.74%%]
 2883584   [ 57.06%%]
 2899968   [ 57.39%%]
 2916352   [ 57.71%%]
 2932736   [ 58.03%%]
 2949120   [ 58.36%%]
 2965504   [ 58.68%%]
 2981888   [ 59.01%%]
 2998272   [ 59.33%%]
 3014656   [ 59.66%%]
 3031040   [ 59.98%%]
 3047424   [ 60.30%%]
 3063808   [ 60.63%%]
 3080192   [ 60.95%%]
 3096576   [ 61.28%%]
 3112960   [ 61.60%%]
 3129344   [ 61.93%%]
 3145728   [ 62.25%%]
 3162112   [ 62.57%%]
 3178496   [ 62.90%%]
 3194880   [ 63.22%%]
 3211264   [ 63.55%%]
 3227648   [ 63.87%%]
 3244032   [ 64.19%%]
 3260416   [ 64.52%%]
 3276800   [ 64.84%%]
 3293184   [ 65.17%%]
 3309568   [ 65.49%%]
 3325952   [ 65.82%%]
 3342336   [ 66.14%%]
 3358720   [ 66.46%%]
 3375104   [ 66.79%%]
 3391488   [ 67.11%%]
 3407872   [ 67.44%%]
 3424256   [ 67.76%%]
 3440640   [ 68.09%%]
 3457024   [ 68.41%%]
 3473408   [ 68.73%%]
 3489792   [ 69.06%%]
 3506176   [ 69.38%%]
 3522560   [ 69.71%%]
 3538944   [ 70.03%%]
 3555328   [ 70.35%%]
 3571712   [ 70.68%%]
 3588096   [ 71.00%%]
 3604480   [ 71.33%%]
 3620864   [ 71.65%%]
 3637248   [ 71.98%%]
 3653632   [ 72.30%%]
 3670016   [ 72.62%%]
 3686400   [ 72.95%%]
 3702784   [ 73.27%%]
 3719168   [ 73.60%%]
 3735552   [ 73.92%%]
 3751936   [ 74.25%%]
 3768320   [ 74.57%%]
 3784704   [ 74.89%%]
 3801088   [ 75.22%%]
 3817472   [ 75.54%%]
 3833856   [ 75.87%%]
 3850240   [ 76.19%%]
 3866624   [ 76.51%%]
 3883008   [ 76.84%%]
 3899392   [ 77.16%%]
 3915776   [ 77.49%%]
 3932160   [ 77.81%%]
 3948544   [ 78.14%%]
 3964928   [ 78.46%%]
 3981312   [ 78.78%%]
 3997696   [ 79.11%%]
 4014080   [ 79.43%%]
 4030464   [ 79.76%%]
 4046848   [ 80.08%%]
 4063232   [ 80.41%%]
 4079616   [ 80.73%%]
 4096000   [ 81.05%%]
 4112384   [ 81.38%%]
 4128768   [ 81.70%%]
 4145152   [ 82.03%%]
 4161536   [ 82.35%%]
 4177920   [ 82.68%%]
 4194304   [ 83.00%%]
 4210688   [ 83.32%%]
 4227072   [ 83.65%%]
 4243456   [ 83.97%%]
 4259840   [ 84.30%%]
 4276224   [ 84.62%%]
 4292608   [ 84.94%%]
 4308992   [ 85.27%%]
 4325376   [ 85.59%%]
 4341760   [ 85.92%%]
 4358144   [ 86.24%%]
 4374528   [ 86.57%%]
 4390912   [ 86.89%%]
 4407296   [ 87.21%%]
 4423680   [ 87.54%%]
 4440064   [ 87.86%%]
 4456448   [ 88.19%%]
 4472832   [ 88.51%%]
 4489216   [ 88.84%%]
 4505600   [ 89.16%%]
 4521984   [ 89.48%%]
 4538368   [ 89.81%%]
 4554752   [ 90.13%%]
 4571136   [ 90.46%%]
 4587520   [ 90.78%%]
 4603904   [ 91.10%%]
 4620288   [ 91.43%%]
 4636672   [ 91.75%%]
 4653056   [ 92.08%%]
 4669440   [ 92.40%%]
 4685824   [ 92.73%%]
 4702208   [ 93.05%%]
 4718592   [ 93.37%%]
 4734976   [ 93.70%%]
 4751360   [ 94.02%%]
 4767744   [ 94.35%%]
 4784128   [ 94.67%%]
 4800512   [ 95.00%%]
 4816896   [ 95.32%%]
 4833280   [ 95.64%%]
 4849664   [ 95.97%%]
 4866048   [ 96.29%%]
 4882432   [ 96.62%%]
 4898816   [ 96.94%%]
 4915200   [ 97.26%%]
 4931584   [ 97.59%%]
 4947968   [ 97.91%%]
 4964352   [ 98.24%%]
 4980736   [ 98.56%%]
 4997120   [ 98.89%%]
 5013504   [ 99.21%%]
 5029888   [ 99.53%%]
 5046272   [ 99.86%%]
 5053420   [100.00%%]
Unpacking: movies.db
Fetching 'airports.csv'
Downloading: airports.csv (203190 bytes)
 16384     [  8.06%%]
 32768     [ 16.13%%]
 49152     [ 24.19%%]
 65536     [ 32.25%%]
 81920     [ 40.32%%]
 98304     [ 48.38%%]
 114688    [ 56.44%%]
 131072    [ 64.51%%]
 147456    [ 72.57%%]
 163840    [ 80.63%%]
 180224    [ 88.70%%]
 196608    [ 96.76%%]
 203190    [100.00%%]
Fetching 'routes.csv'
Downloading: routes.csv (377280 bytes)
 16384     [  4.34%%]
 32768     [  8.69%%]
 49152     [ 13.03%%]
 65536     [ 17.37%%]
 81920     [ 21.71%%]
 98304     [ 26.06%%]
 114688    [ 30.40%%]
 131072    [ 34.74%%]
 147456    [ 39.08%%]
 163840    [ 43.43%%]
 180224    [ 47.77%%]
 196608    [ 52.11%%]
 212992    [ 56.45%%]
 229376    [ 60.80%%]
 245760    [ 65.14%%]
 262144    [ 69.48%%]
 278528    [ 73.83%%]
 294912    [ 78.17%%]
 311296    [ 82.51%%]
 327680    [ 86.85%%]
 344064    [ 91.20%%]
 360448    [ 95.54%%]
 376832    [ 99.88%%]
 377280    [100.00%%]
Fetching 'haarcascade_frontalface_default.xml'
Downloading: haarcascade_frontalface_default.xml (930127 bytes)
 16384     [  1.76%%]
 32768     [  3.52%%]
 49152     [  5.28%%]
 65536     [  7.05%%]
 81920     [  8.81%%]
 98304     [ 10.57%%]
 114688    [ 12.33%%]
 131072    [ 14.09%%]
 147456    [ 15.85%%]
 163840    [ 17.61%%]
 180224    [ 19.38%%]
 196608    [ 21.14%%]
 212992    [ 22.90%%]
 229376    [ 24.66%%]
 245760    [ 26.42%%]
 262144    [ 28.18%%]
 278528    [ 29.95%%]
 294912    [ 31.71%%]
 311296    [ 33.47%%]
 327680    [ 35.23%%]
 344064    [ 36.99%%]
 360448    [ 38.75%%]
 376832    [ 40.51%%]
 393216    [ 42.28%%]
 409600    [ 44.04%%]
 425984    [ 45.80%%]
 442368    [ 47.56%%]
 458752    [ 49.32%%]
 475136    [ 51.08%%]
 491520    [ 52.84%%]
 507904    [ 54.61%%]
 524288    [ 56.37%%]
 540672    [ 58.13%%]
 557056    [ 59.89%%]
 573440    [ 61.65%%]
 589824    [ 63.41%%]
 606208    [ 65.17%%]
 622592    [ 66.94%%]
 638976    [ 68.70%%]
 655360    [ 70.46%%]
 671744    [ 72.22%%]
 688128    [ 73.98%%]
 704512    [ 75.74%%]
 720896    [ 77.51%%]
 737280    [ 79.27%%]
 753664    [ 81.03%%]
 770048    [ 82.79%%]
 786432    [ 84.55%%]
 802816    [ 86.31%%]
 819200    [ 88.07%%]
 835584    [ 89.84%%]
 851968    [ 91.60%%]
 868352    [ 93.36%%]
 884736    [ 95.12%%]
 901120    [ 96.88%%]
 917504    [ 98.64%%]
 930127    [100.00%%]
Fetching 'SampleSuperstore.csv.zip'
Downloading: SampleSuperstore.csv.zip (167457 bytes)

 16384     [  9.78%%]
 32768     [ 19.57%%]
 49152     [ 29.35%%]
 65536     [ 39.14%%]
 81920     [ 48.92%%]
 98304     [ 58.70%%]
 114688    [ 68.49%%]
 131072    [ 78.27%%]
 147456    [ 88.06%%]
 163840    [ 97.84%%]
 167457    [100.00%%]
Unpacking: SampleSuperstore.csv
Fetching 'emissions.csv'
Downloading: emissions.csv (298241 bytes)

 16384     [  5.49%%]
 32768     [ 10.99%%]
 49152     [ 16.48%%]
 65536     [ 21.97%%]
 81920     [ 27.47%%]
 98304     [ 32.96%%]
 114688    [ 38.45%%]
 131072    [ 43.95%%]
 147456    [ 49.44%%]
 163840    [ 54.94%%]
 180224    [ 60.43%%]
 196608    [ 65.92%%]
 212992    [ 71.42%%]
 229376    [ 76.91%%]
 245760    [ 82.40%%]
 262144    [ 87.90%%]
 278528    [ 93.39%%]
 294912    [ 98.88%%]
 298241    [100.00%%]
Fetching 'titanic_all.csv'
Downloading: titanic_all.csv (54758 bytes)

 16384     [ 29.92%%]
 32768     [ 59.84%%]
 49152     [ 89.76%%]
 54758     [100.00%%]

# Discard the output from one aggregation of each type, to avoid measuring Numba compilation times
tf.shade(cvs.polygons(county_info, geometry='boundary', agg=ds.mean('unemployment')));
tf.shade(cvs.line(county_info, geometry='boundary', agg=ds.any()));
tf.shade(cvs.line(county_info, geometry='boundary', agg=ds.any(), line_width=1.5));
%%time
cvs = ds.Canvas(plot_width=600, plot_height=600)
agg = cvs.polygons(county_info, geometry='boundary', agg=ds.mean('unemployment'))
filled = tf.shade(agg)
CPU times: user 12.8 ms, sys: 3.7 ms, total: 16.5 ms
Wall time: 16.3 ms
%%time
agg = cvs.line(county_info, geometry='boundary', agg=ds.any())
unfilled = tf.shade(agg)
CPU times: user 11.1 ms, sys: 0 ns, total: 11.1 ms
Wall time: 11 ms
%%time
agg = cvs.line(county_info, geometry='boundary', agg=ds.any(), line_width=3.5)
antialiased = tf.shade(agg)
CPU times: user 1.32 s, sys: 3.73 ms, total: 1.33 s
Wall time: 1.32 s
tf.Images(filled, unfilled, antialiased)






Geopandas import#

The .from_geopandas static method on each spatialpandas ExtensionArray can be used to import a geopandas GeoSeries of Polygon/MultiPolygon objects:

import geopandas

world = geopandas.read_file(geopandas.datasets.get_path('naturalearth_lowres'))
world = world.to_crs(epsg=4087) # simple cylindrical projection
world['boundary'] = world.geometry.boundary
world['centroid'] = world.geometry.centroid
world.head()
pop_est continent name iso_a3 gdp_md_est geometry boundary centroid
0 889953.0 Oceania Fiji FJI 5496 MULTIPOLYGON (((20037508.343 -1788585.027, 200... MULTILINESTRING ((20037508.343 -1788585.027, 2... POINT (18240050.853 -1927642.748)
1 58005463.0 Africa Tanzania TZA 63177 POLYGON ((3774143.866 -105753.516, 3792946.708... LINESTRING (3774143.866 -105753.516, 3792946.7... POINT (3868685.134 -696607.587)
2 603253.0 Africa W. Sahara ESH 907 POLYGON ((-964649.018 3078699.247, -964597.245... LINESTRING (-964649.018 3078699.247, -964597.2... POINT (-1351177.179 2704081.005)
3 37589262.0 North America Canada CAN 1736425 MULTIPOLYGON (((-13674486.249 5454655.049, -13... MULTILINESTRING ((-13674486.249 5454655.049, -... POINT (-10925159.920 6842706.256)
4 328239523.0 North America United States of America USA 21433226 MULTIPOLYGON (((-13674486.249 5454655.049, -13... MULTILINESTRING ((-13674486.249 5454655.049, -... POINT (-12534511.869 5087927.236)

Convert the geopandas GeoDataFrame to a spatialpandas GeoDataFrame for Datashader to use:

%%time
df_world = sp.GeoDataFrame(world)
df_world.head()
CPU times: user 1.02 s, sys: 3.85 ms, total: 1.03 s
Wall time: 1.03 s
pop_est continent name iso_a3 gdp_md_est geometry boundary centroid
0 889953.0 Oceania Fiji FJI 5496 MultiPolygon([[[20037508.342789244, -1788585.0... MultiLine([[20037508.342789244, -1788585.02662... Point([18240050.853101123, -1927642.747763679])
1 58005463.0 Africa Tanzania TZA 63177 MultiPolygon([[[3774143.866463884, -105753.516... MultiLine([[3774143.866463884, -105753.5162536... Point([3868685.134175233, -696607.5874618533])
2 603253.0 Africa W. Sahara ESH 907 MultiPolygon([[[-964649.017849934, 3078699.247... MultiLine([[-964649.017849934, 3078699.2471913... Point([-1351177.1786789333, 2704081.0047017606])
3 37589262.0 North America Canada CAN 1736425 MultiPolygon([[[-13674486.24904573, 5454655.04... MultiLine([[-13674486.24904573, 5454655.048870... Point([-10925159.919581091, 6842706.256033208])
4 328239523.0 North America United States of America USA 21433226 MultiPolygon([[[-13674486.24904573, 5454655.04... MultiLine([[-13674486.24904573, 5454655.048870... Point([-12534511.869278513, 5087927.235586329])

Since version 0.16, Datashader supports direct use of geopandas GeoDataFrames without having to convert them to spatialpandas. See GeoPandas.

Geopandas/shapely export#

A MultiPolygonArray can be converted to a geopandas GeometryArray using the to_geopandas method.

%%time
pd.Series(df_world.boundary.array.to_geopandas())
CPU times: user 30.8 ms, sys: 3.94 ms, total: 34.8 ms
Wall time: 34.1 ms
0      MULTILINESTRING ((20037508.343 -1788585.027, 2...
1      MULTILINESTRING ((3774143.866 -105753.516, 379...
2      MULTILINESTRING ((-964649.018 3078699.247, -96...
3      MULTILINESTRING ((-13674486.249 5454655.049, -...
4      MULTILINESTRING ((-13674486.249 5454655.049, -...
                             ...                        
172    MULTILINESTRING ((2096126.508 5110552.294, 209...
173    MULTILINESTRING ((2234260.104 4740944.605, 220...
174    MULTILINESTRING ((2292095.761 4659322.808, 228...
175    MULTILINESTRING ((-6866186.192 1197797.721, -6...
176    MULTILINESTRING ((3432408.751 390639.196, 3334...
Length: 177, dtype: geometry

Individual elements of a MultiPolygonArray can be converted into shapely shapes using the to_shapely method

df_world.geometry.array[3].to_shapely()
../_images/3fe9c3d94b4d35e95398eb1089a00445401d52736ade3fdd8ce909f94a7e4f76.svg

Plotting as filled polygons#

# Discard the output to avoid measuring Numba compilation times
tf.shade(cvs.polygons(df_world, geometry='geometry', agg=ds.mean('pop_est')));
%%time
cvs = ds.Canvas(plot_width=650, plot_height=400)
agg = cvs.polygons(df_world, geometry='geometry', agg=ds.mean('pop_est'))
tf.shade(agg)
CPU times: user 32.5 ms, sys: 17 µs, total: 32.5 ms
Wall time: 32.2 ms

Plotting as centroid points#

# Discard the output to avoid measuring Numba compilation times
cvs.points(df_world, geometry='centroid', agg=ds.mean('pop_est'));
%%time
agg = cvs.points(df_world, geometry='centroid', agg=ds.mean('pop_est'))
tf.spread(tf.shade(agg), 2)
CPU times: user 2.52 s, sys: 11.7 ms, total: 2.53 s
Wall time: 2.53 s

Polygon Perimeter/Area calculation#

The spatialpandas library provides highly optimized versions of some of the geometric operations supported by a geopandas GeoSeries, including parallelized Numba implementations of the length and area properties:

{"MultiPolygon2dArray length": df_world.geometry.array.length[:4],
 "GeoPandas length":              world.geometry.array.length[:4],
 "MultiPolygonArray area":     df_world.geometry.array.area[:4],
 "GeoPandas area":                world.geometry.array.area[:4],}
{'MultiPolygon2dArray length': array([1.00087464e+06, 4.14783890e+06, 3.07933564e+06, 1.01975651e+08]),
 'GeoPandas length': array([1.00087464e+06, 4.14783890e+06, 3.07933564e+06, 1.01975651e+08]),
 'MultiPolygonArray area': array([2.03168679e+10, 9.45536148e+11, 1.06620822e+11, 2.12274866e+13]),
 'GeoPandas area': array([2.03168679e+10, 9.45536148e+11, 1.06620822e+11, 2.12274866e+13])}

Speed differences:

# Duplicate world 1000 times
df_world_large = pd.concat([df_world.geometry] * 1000)
world_large = pd.concat([world.geometry] * 1000)
length_ds = %timeit -o world_large.array.length
length_gp = %timeit -o  df_world_large.array.length
print("\nMultiPolygonArray.length speedup: %.2f" % (length_ds.average / length_gp.average))
31.3 ms ± 77.8 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)
14.9 ms ± 49.6 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

MultiPolygonArray.length speedup: 2.10
area_ds = %timeit -o world_large.array.area
area_gp = %timeit -o df_world_large.array.area
print("\nMultiPolygonArray.area speedup: %.2f" % (area_ds.average / area_gp.average))
13.4 ms ± 53.2 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
4.08 ms ± 72.5 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

MultiPolygonArray.area speedup: 3.29

Other GeoPandas operations could be sped up similarly by adding them to spatialpandas.

Parquet support#

spatialpandas geometry arrays can be stored in Parquet files, which support efficient chunked columnar access that is particularly important when working with Dask for large files. To create such a file, use .to_parquet:

df_world.to_parquet('df_world.parq')

A parquet file containing geometry arrays should be read using the spatialpandas.io.read_parquet function:

from spatialpandas.io import read_parquet
read_parquet('df_world.parq').head(2)
pop_est continent name iso_a3 gdp_md_est geometry boundary centroid
0 889953.0 Oceania Fiji FJI 5496 MultiPolygon([[[20037508.342789244, -1788585.0... MultiLine([[20037508.342789244, -1788585.02662... Point([18240050.853101123, -1927642.747763679])
1 58005463.0 Africa Tanzania TZA 63177 MultiPolygon([[[3774143.866463884, -105753.516... MultiLine([[3774143.866463884, -105753.5162536... Point([3868685.134175233, -696607.5874618533])

Dask support#

For large collections of polygons, you can use Dask to parallelize the rendering. If you are starting with a Pandas dataframe with a geometry column, just use the standard dask.dataframe.from_pandas method:

ddf = dd.from_pandas(df_world, npartitions=2).pack_partitions(npartitions=100).persist()

tf.shade(cvs.polygons(ddf, geometry='geometry', agg=ds.mean('gdp_md_est')), cmap=cc.kg)

Here we’ve used pack_partitions to re-sort and re-partition the dataframe such that each partition contains geometry objects that are relatively close together in space. This partitioning makes it faster for Datashader to identify which partitions are needed in order to render a particular view, which is useful when zooming into local regions of large datasets. (This particular dataset is quite small, and unlikely to benefit, of course!)

Interactive example using HoloViews#

As you can see above, HoloViews can easily invoke Datashader on polygons using rasterize, with full interactive redrawing at each new zoom level as long as you have a live Python process running. The code for the world population example would be:

out = rasterize(hv.Polygons(ddf, vdims=['pop_est']), aggregator=ds.sum('pop_est'))
out.opts(width=700, height=500, tools=["hover"]);

However, we’ve used a semicolon to suppress the output, because we’ll actually use a more complex example with a custom callback function cb to update the plot title whenever you zoom in. That way, you’ll be able to see the number of partitions that the spatial index has determined are needed to cover the current viewport:

def compute_partitions(el):
    n = ddf.cx_partitions[slice(*el.range('x')), slice(*el.range('y'))].npartitions
    return el.opts(title=f'Population by country (npartitions: {n})')

out.apply(compute_partitions).opts(width=700, height=500, tools=["hover"], clim=(0, 1.3e9))

Now, if you zoom in with this page backed by a live Python process, you’ll not only see the plot redraw at full resolution whenever you zoom in, you’ll see how many partitions of the dataset are needed to render it, ranging from 100 for the full map down to 1 when zoomed into a small area.

A larger example with polygons for the footprints of a million buildings in the New York City area can be run online at PyViz examples.

This web page was generated from a Jupyter notebook and not all interactivity will work on this website. Right click to download and run locally for full Python-backed interactivity.

Right click to download this notebook from GitHub.