[PYTHON] Utilisez cartopy avec Google Colaboratory sans souffrir de bugs

Si vous voulez faire de la science des données avec Python (pandas ou NumPy), la norme actuelle de facto est d'utiliser matplotlib comme bibliothèque de dessins, et [pour dessiner des données et des cartes géospatiales Il est préférable d'utiliser cartopy. Le cartopy est 2020- lorsque j'essaye de l'utiliser avec Google Colaboratory qui est Jupyter notebook sur le cloud Google. 04 Actuellement, la méthode officielle est en proie à des bugs et est pratiquement inutilisable. Voici un résumé des solutions de contournement et leurs explications.

Conclusion

Installez avec l'un des éléments suivants.

modèle 1

!grep '^deb ' /etc/apt/sources.list | \
  sed 's/^deb /deb-src /g' | \
  tee /etc/apt/sources.list.d/deb-src.list
!apt-get -qq update

!apt-get -qq build-dep python3-cartopy
!pip uninstall -y shapely

!pip install --no-binary cartopy cartopy==0.17.0

Motif 2

!grep '^deb ' /etc/apt/sources.list | \
  sed 's/^deb /deb-src /g' | \
  tee /etc/apt/sources.list.d/deb-src.list
!apt-get update

!apt-get -qq build-dep python3-cartopy
!apt-get -qq remove python-shapely python3-shapely

!pip install --no-binary shapely shapely --force
!pip install --no-binary cartopy cartopy==0.17.0

Je m'inquiète des bugs si c'est la méthode officielle

Le bloc-notes officiel de Google Colaboratory comment installer cartopy, emballage du système d'exploitation comme suit: Il est censé être possible en utilisant le système apt.

!apt-get -qq install python-cartopy python3-cartopy
import cartopy

Cependant, le cartopy installé de cette façon a un bogue qui peut être supprimé avec un code simple comme celui-ci:

Problème 1: gridlines () échoue

Je ne peux pas dessiner la grille car j'obtiens une erreur avec gridlines ().

Exemple de code:

import cartopy.crs as ccrs
import matplotlib.pyplot as plt

ax = plt.axes(projection=ccrs.PlateCarree())
ax.gridlines()
ax.coastlines()

Erreur:

---------------------------------------------------------------------------
ValueError                                Traceback (most recent call last)
<ipython-input-4-3e1ebed7d096> in <module>()
      3 
      4 ax = plt.axes(projection=ccrs.PlateCarree())
----> 5 ax.gridlines()
      6 ax.coastlines()

4 frames
/usr/local/lib/python3.6/dist-packages/matplotlib/ticker.py in _validate_steps(steps)
   2108         steps = np.asarray(steps)
   2109         if np.any(np.diff(steps) <= 0) or steps[-1] > 10 or steps[0] < 1:
-> 2110             raise ValueError('steps argument must be an increasing sequence '
   2111                              'of numbers between 1 and 10 inclusive')
   2112         if steps[0] != 1:

ValueError: steps argument must be an increasing sequence of numbers between 1 and 10 inclusive

Problème 2: Chute avec littoraux ()

Dessiner un trait de côte en utilisant coastlines () entraînera une "session plantée pour une raison inconnue" avec le journal d'exécution suivant:

Exemple de code:

import cartopy.crs as ccrs
import matplotlib.pyplot as plt

ax = plt.axes(projection=ccrs.PlateCarree())
ax.coastlines()

Journal des erreurs (journal d'exécution):

Apr 14, 2020, 6:18:57 PM	WARNING	warn("IPython.utils.traitlets has moved to a top-level traitlets package.")
Apr 14, 2020, 6:18:57 PM	WARNING	/usr/local/lib/python3.6/dist-packages/IPython/utils/traitlets.py:5: UserWarning: IPython.utils.traitlets has moved to a top-level traitlets package.
Apr 14, 2020, 6:18:57 PM	WARNING	WARNING:root:kernel e5263554-c566-4983-aea5-418e4cb6441a restarted
Apr 14, 2020, 6:18:57 PM	INFO	KernelRestarter: restarting kernel (1/5), keep random ports
Apr 14, 2020, 6:18:54 PM	WARNING	python3: geos_ts_c.cpp:3991: int GEOSCoordSeq_getSize_r(GEOSContextHandle_t, const geos::geom::CoordinateSequence*, unsigned int*): Assertion `0 != cs' failed.

Cause de chaque problème

question 1

La cause du problème 1 est que la cartouche installée est aussi ancienne que la v0.14.2. Bien qu'il ait été signalé dans le [problème # 1374] de cartopy (https://github.com/SciTools/cartopy/issues/1374), le bogue lui-même est PR # 773. Il a été corrigé dans / cartopy / pull / 773) et a été corrigé depuis la v0.16.0 en février 2018.

À propos, la v0.14.2 est la version publiée en avril 2016, et la raison pour laquelle une telle ancienne est installée est que le système d'exploitation est Ubuntu 18.04.3 LTS. Comme le dit LTS, il s'agit d'une version prise en charge à long terme, et la première version, 18.04, a été publiée en avril 2018. Comme il s'agit d'une version de support à long terme, vous pouvez l'utiliser en toute confiance pendant une longue période, mais s'il s'agit d'un logiciel mineur ou d'un logiciel qui n'est pas encore stable, il est un peu difficile que la version avec le bogue soit emballée et utilisée tout le temps. (Voir Informations sur le package).

In [1]: cartopy.__version__

Out[1]: '0.14.2'

In [2]: !cat /etc/os-release

Out[2]:
NAME="Ubuntu"
VERSION="18.04.3 LTS (Bionic Beaver)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 18.04.3 LTS"
VERSION_ID="18.04"
HOME_URL="https://www.ubuntu.com/"
SUPPORT_URL="https://help.ubuntu.com/"
BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/"
PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy"
VERSION_CODENAME=bionic
UBUNTU_CODENAME=bionic

Problème 2

Le problème 2 est que cartopy et Shapely utilisé par cartopy utilisent des versions différentes de GEOS et sont incompatibles. Signalé comme [Issue # 871] de cartopy (https://github.com/SciTools/cartopy/issues/871) et Issue # 1490 Issue # 805 traite de la réponse fondamentale, mais elle n'a pas encore été résolue.

Dans Debian et Ubuntu, si la version du paquet de bibliothèque augmente, les paquets qui en dépendent seront reconstruits, donc il ne devrait pas être lié à une version différente de la bibliothèque. En fait, si vous insérez une cartopy avec apt, la version du package deb Shapely 1.6.4 fournie par le système d'exploitation sera incluse avec la cartopy qui lui est liée, comme indiqué ci-dessous. Si ce Shapely est utilisé, aucun problème ne se produira.

Paquets Deb entrés avec ʻapt-get install` au début:

python-pkg-resources (39.0.1-2 Ubuntu:18.04/bionic [all])
python-pyshp (1.2.12+ds-1 Ubuntu:18.04/bionic [all])
python-shapely (1.6.4-1 Ubuntu:18.04/bionic [amd64])
python-six (1.11.0-2 Ubuntu:18.04/bionic [all])
python-cartopy (0.14.2+dfsg1-2build3 Ubuntu:18.04/bionic [amd64])
python3-pkg-resources (39.0.1-2 Ubuntu:18.04/bionic [all])
python3-pyshp (1.2.12+ds-1 Ubuntu:18.04/bionic [all])
python3-shapely (1.6.4-1 Ubuntu:18.04/bionic [amd64])
python3-six (1.11.0-2 Ubuntu:18.04/bionic [all])
python3-cartopy (0.14.2+dfsg1-2build3 Ubuntu:18.04/bionic [amd64])

Cependant, comme indiqué ci-dessous, Google Colaboratory semble avoir inclus la dernière version de Shapely v1.7.0 avec pip depuis le début.

In [3]: !pip list | grep Shapely

Out[3]: Shapely                  1.7.0

Si vous importez simplement dans cet état, cartopy sera apt et Shapely sera pip. C'est la cause de l'incompatibilité. C'est un problème.

In [4]:
import shapely
shapely.__version__

Out[4]: '1.7.0'

A part: si seul le problème 2 est en fait une contre-mesure, c'est facile.

En ce qui concerne le problème 2, la combinaison de pip et apt est mauvaise, donc c'est en fait facile. Si vous exécutez ce qui suit avant ou après ʻapt-get install au début, Shapely utilisera celui que vous avez mis avec apt (version deb) (ʻimport cartopy avant pip uninstall. Et, notez que ce sera «important» dedans).

!pip uninstall -y shapely

contre-mesure

Puisque la cause est la suivante, la politique de contre-mesures est la suivante.

Plus précisément, faites ceci.

  1. Supprimez le Shapely entré avec pip
  2. Créez la dernière version de cartopy à partir des sources avec pip en utilisant GEOS avec Shapely lié

apt-get build-dep

Lors de l'importation depuis la source, les bibliothèques dépendantes telles que GEOS doivent être incluses. Il est difficile de les mettre un par un, donc cette fois j'utiliserai ʻapt-get build-dep`.

ʻApt-get build-dep` est une commande qui installe le paquet deb nécessaire pour construire le paquet source pour le paquet deb spécifié. Dans ce cas, l'environnement requis pour construire cartopy v0.17.0 sera préparé en fonction des informations de construction du paquet source du paquet deb de cartopy v0.14.2. Bien sûr, s'il y a des changements dans les dépendances entre la v0.14.2 et la v0.17.0, cela ne fonctionnera pas, mais s'il n'y a pas de changements majeurs, ça va (en fait, cette fois ça a marché).

Modifier apt sources.list

Ensuite, je veux aller à ʻapt-get build-dep` immédiatement, mais même si je l'exécute soudainement, une erreur se produit.

In [5]: !apt-get build-dep cartopy

Out[5]:
Reading package lists... Done
E: Unable to find a source package for cartopy

Les informations du paquet source utilisées par apt-get build-dep sont / etc / apt / sources.list (et/ etc / apt / sources.list.d / *) qui est le paramètre source d'acquisition de paquet d'apt. C'est parce qu'il est commenté par défaut.

In [6]: !grep deb /etc/apt/sources.list

Out[6]:
deb http://archive.ubuntu.com/ubuntu/ bionic main restricted
# deb-src http://archive.ubuntu.com/ubuntu/ bionic main restricted
deb http://archive.ubuntu.com/ubuntu/ bionic-updates main restricted
# deb-src http://archive.ubuntu.com/ubuntu/ bionic-updates main restricted
deb http://archive.ubuntu.com/ubuntu/ bionic universe
# deb-src http://archive.ubuntu.com/ubuntu/ bionic universe
deb http://archive.ubuntu.com/ubuntu/ bionic-updates universe
# deb-src http://archive.ubuntu.com/ubuntu/ bionic-updates universe
deb http://archive.ubuntu.com/ubuntu/ bionic multiverse
# deb-src http://archive.ubuntu.com/ubuntu/ bionic multiverse
deb http://archive.ubuntu.com/ubuntu/ bionic-updates multiverse
# deb-src http://archive.ubuntu.com/ubuntu/ bionic-updates multiverse
deb http://archive.ubuntu.com/ubuntu/ bionic-backports main restricted universe multiverse
# deb-src http://archive.ubuntu.com/ubuntu/ bionic-backports main restricted universe multiverse
# deb http://archive.canonical.com/ubuntu bionic partner
# deb-src http://archive.canonical.com/ubuntu bionic partner
deb http://security.ubuntu.com/ubuntu/ bionic-security main restricted
# deb-src http://security.ubuntu.com/ubuntu/ bionic-security main restricted
deb http://security.ubuntu.com/ubuntu/ bionic-security universe
# deb-src http://security.ubuntu.com/ubuntu/ bionic-security universe
deb http://security.ubuntu.com/ubuntu/ bionic-security multiverse
# deb-src http://security.ubuntu.com/ubuntu/ bionic-security multiverse
deb https://cloud.r-project.org/bin/linux/ubuntu bionic-cran35/

C'est la seule cause, donc vous pouvez le résoudre en préparant simplement un fichier avec la ligne commençant par deb remplacée par deb-src et en mettant à jour les informations du paquet avec ʻapt-get update`.

In [7]:
!grep '^deb ' /etc/apt/sources.list | \
  sed 's/^deb /deb-src /g' | \
  tee /etc/apt/sources.list.d/deb-src.list
!apt-get -qq update

Cela passera également le ʻapt-get build-dep` ci-dessus.

Installation

Après cela, si vous utilisez pip install --no-binary pour construire sans utiliser de packages binaires, la procédure décrite au début sera utilisée. Je pense qu'il y a les deux cas où il n'y a pas de problème avec Shapely d'apt et les cas où vous souhaitez utiliser la dernière version initialement incluse dans Google Colaboratory, donc je vais montrer deux modèles. C'est une bonne idée de le changer en fonction du Shapey que vous souhaitez utiliser.

Modèle 1: lors de l'utilisation de la version du package deb d'apt Shapely (v1.6.4)

!grep '^deb ' /etc/apt/sources.list | \
  sed 's/^deb /deb-src /g' | \
  tee /etc/apt/sources.list.d/deb-src.list
!apt-get -qq update

!apt-get -qq build-dep python3-cartopy
!pip uninstall -y shapely

!pip install --no-binary cartopy cartopy==0.17.0

Motif 2: lors de l'utilisation de la dernière version de Shapely (v1.7.0) à partir de la source

!grep '^deb ' /etc/apt/sources.list | \
  sed 's/^deb /deb-src /g' | \
  tee /etc/apt/sources.list.d/deb-src.list
!apt-get update

!apt-get -qq build-dep python3-cartopy
!apt-get -qq remove python-shapely python3-shapely

!pip install --no-binary shapely shapely --force
!pip install --no-binary cartopy cartopy==0.17.0

Contrôle de fonctionnement

Les deux programmes Python des questions 1 et 2 fonctionnent correctement. Les ondes de la galerie officielle fonctionne également comme indiqué ci-dessous.

import matplotlib.pyplot as plt
import numpy as np

import cartopy.crs as ccrs


def sample_data(shape=(73, 145)):
    """Return ``lons``, ``lats`` and ``data`` of some fake data."""
    nlats, nlons = shape
    lats = np.linspace(-np.pi / 2, np.pi / 2, nlats)
    lons = np.linspace(0, 2 * np.pi, nlons)
    lons, lats = np.meshgrid(lons, lats)
    wave = 0.75 * (np.sin(2 * lats) ** 8) * np.cos(4 * lons)
    mean = 0.5 * np.cos(2 * lats) * ((np.sin(2 * lats)) ** 2 + 2)

    lats = np.rad2deg(lats)
    lons = np.rad2deg(lons)
    data = wave + mean

    return lons, lats, data


def main():
    fig = plt.figure(figsize=(10, 5))
    ax = fig.add_subplot(1, 1, 1, projection=ccrs.Mollweide())

    lons, lats, data = sample_data()

    ax.contourf(lons, lats, data,
                transform=ccrs.PlateCarree(),
                cmap='nipy_spectral')
    ax.coastlines()
    ax.set_global()
    plt.show()


main()

waves.png

Postscript (2020-04-15): retour à l'état initial

Étant donné que le contenu (état) du système de fichiers du système d'exploitation change pendant l'installation, il est préférable de savoir comment revenir à l'état initial lors d'une tentative et d'une erreur de l'installation. Vous pouvez le réinitialiser par la méthode suivante.

  1. Sélectionnez "Reset Runtime to Factory Settings" dans le menu "Runtime".

Avec "Restart Runtime", l'état d'exécution du code est dans l'état initial (rien n'est en mémoire), mais le système de fichiers reste modifié.

Recommended Posts

Utilisez cartopy avec Google Colaboratory sans souffrir de bugs
Comment utiliser le modèle japonais Spacy avec Google Colaboratory
Je ne peux pas utiliser la commande darknet dans Google Colaboratory!
Comment utiliser Google Colaboratory
■ [Google Colaboratory] Utiliser l'analyse morphologique (janome)
■ [Google Colaboratory] Utiliser l'analyse morphologique (MeCab)
Extraits (scraping) enregistrés dans Google Colaboratory
Collaboratoire Google
Utilisez le désassembleur métabolique sur Google Colaboratory
Utilisez tensorflow dans un environnement sans racine
Comment utiliser Google Test en langage C
Utilisez TPU et Keras avec Google Colaboratory
Extraits enregistrés dans Google Colaboratory (conversion de texte PDF)
[Explication de la mise en œuvre] Comment utiliser la version japonaise de BERT dans Google Colaboratory (PyTorch)
Comment charger des fichiers dans Google Drive avec Google Colaboratory
Créer un environnement pour utiliser CaboCha avec Google Colaboratory
Résumé de la configuration de Google Colaboratory
Utilisez config.ini avec Python
Utiliser DataFrame en Java
Utiliser des dates en Python
Utiliser ujson dans les requêtes
Utiliser le profileur en Python
Utilisez «% tensorflow_version 2.x» lorsque vous utilisez TPU avec Tensorflow 2.1.0 dans Colaboratory
Gratter les résultats de recherche de Google Actualités en Python (2) Utiliser Beautiful Soup