[PYTHON] Remarque: préparez l'environnement de CmdStanPy avec docker

Afin de lire "Modélisation statistique Bayes avec Stan et R", j'ai préparé un environnement CmdStanPy avec docker. Il semblait y avoir peu de documents japonais sur la construction de l'environnement pour CmdStanPy, donc je pense que cela pourrait être utile pour quelqu'un, alors je vais l'écrire.

introduction

Comme vous pouvez le voir dans le Document officiel, veuillez faire attention si vous utilisez un environnement où PyStan est déjà installé.

Note for PyStan users: PyStan and CmdStanPy should be installed in separate environments. If you already have PyStan installed, you should take care to install CmdStanPy in its own virtual environment.

J'ai préparé l'environnement avec docker car il semble gênant en raison d'autres problèmes de dépendance [^ 1].

Qu'est-ce que CmdStanPy?

L'emballage léger de CmdStan par Python

Pourquoi CmdStanPy?

Si vous voulez utiliser Stan depuis Python, vous utiliserez probablement PyStan en général [^ 2]. Donc, la raison pour laquelle j'ai décidé d'utiliser CmdStanPy est qu'il fonctionne plus rapidement (actuellement) que PyStan.

Les détails sont les suivants:

J'ai également préparé un environnement PyStan au début, mais avec un exemple simple appelé Eight schools (voir cette partie du document PyStan). Il a fallu plus d'une minute pour compiler mon modèle.

Après avoir vérifié si ma méthode d'installation était mauvaise ou normale, [cet échange] dans la communauté de Stan (https://discourse.mc-stan.org/t/why-is-it) -so-slow-for-stan-to-compile-model / 6004) a été trouvé. Selon

Stan compilation speedup was introduced in Stan 2.20, but Rstan is only up to Stan 2.19.2.

right now we have lightweight wrappers CmdStanPy 11 (still in beta) and CmdStanR 18 (almost to beta release) which use the latest CmdStan (now at 2.21, 2.22 coming soon) - or any version of CmdStan that you’d like.

Cet échange lui-même remonte à deux ans, mais quand j'ai vérifié la version de PyStan dans mon environnement PyStan, c'était la 2.19.1.1, qui semblait être celle avant l'introduction de speedup [^ 3]. De plus, même en écrivant Stackoverflow ici, CmdStanPy a rendu la compilation plus de 3 fois plus rapide. Il y avait une description.

J'ai donc décidé d'essayer CmdStanPy.

environnement

Construction d'environnement avec Docker

Dockerfile


FROM ubuntu:20.04

RUN apt-get -y update
RUN apt-get -y install python3
RUN apt-get -y install python3-pip
RUN pip3 install --upgrade pip
RUN pip3 install cmdstanpy[all]
RUN python3 -c 'import cmdstanpy; cmdstanpy.install_cmdstan()'

WORKDIR /workdir

Construisez comme suit dans le répertoire où se trouve ce Dockerfile [^ 4](remplacez YOUR_TAG par un nom de TAG approprié),

docker image build -t YOUR_TAG .

Démarrer (je monte le répertoire actuel sur / workdir parce que je veux utiliser le code source local)


docker container run -it --rm --net=host  \
		--mount type=bind,src=`pwd`,dst=/workdir \
		YOUR_TAG \
		bash

Courir

Dans le répertoire où vous avez démarré le conteneur Docker

Je vais préparer.

8schools.stan


data {
    int<lower=0> J; // number of schools
    vector[J] y; // estimated treatment effects
    vector<lower=0>[J] sigma; // s.e. of effect estimates
}
parameters {
    real mu;
    real<lower=0> tau;
    vector[J] eta;
}
transformed parameters {
    vector[J] theta;
    theta = mu + tau * eta;
}
model {
    eta ~ normal(0, 1);
    y ~ normal(theta, sigma);
}

JSON:8schools.data.json


{
    "J": 8,
    "y": [28,  8, -3,  7, -1,  1, 18, 12],
    "sigma": [15, 10, 16, 11,  9, 11, 10, 18]
}

run-cmdstanpy.py


from cmdstanpy import CmdStanModel


print("Compile started")
model = CmdStanModel(stan_file="8schools.stan")
print("Compile finished")
print(model)
print("========================================")
data = "8schools.data.json"
print("Sampling started")
fit = model.sample(data=data)
print("Sampling finished")
print(fit)

Si vous exécutez python3 run-cmdstanpy.py dans / workdir dans le conteneur démarré dans la section" Construction de l'environnement avec Docker "et obtenez le résultat suivant, cela réussit pour le moment.

Compile started
INFO:cmdstanpy:compiling stan program, exe file: /workdir/8schools
INFO:cmdstanpy:compiler options: stanc_options=None, cpp_options=None
INFO:cmdstanpy:compiled model file: /workdir/8schools
Compile finished
CmdStanModel: name=8schools
	 stan_file=/workdir/8schools.stan
	 exe_file=/workdir/8schools
	 compiler_optons=stanc_options=None, cpp_options=None
========================================
Sampling started
INFO:cmdstanpy:start chain 1
INFO:cmdstanpy:start chain 2
INFO:cmdstanpy:start chain 3
INFO:cmdstanpy:start chain 4
INFO:cmdstanpy:finish chain 3
INFO:cmdstanpy:finish chain 1
INFO:cmdstanpy:finish chain 4
INFO:cmdstanpy:finish chain 2
Sampling finished
CmdStanMCMC: model=8schools chains=4['method=sample', 'algorithm=hmc', 'adapt', 'engaged=1']
 csv_files:
	/tmp/tmpd0ii4fo_/8schools-202009110125-1-0qknvwdc.csv
	/tmp/tmpd0ii4fo_/8schools-202009110125-2-qfoj4mom.csv
	/tmp/tmpd0ii4fo_/8schools-202009110125-3-cbn8wxph.csv
	/tmp/tmpd0ii4fo_/8schools-202009110125-4-h_5980t6.csv
 output_files:
	/tmp/tmpd0ii4fo_/8schools-202009110125-1-0qknvwdc-stdout.txt
	/tmp/tmpd0ii4fo_/8schools-202009110125-2-qfoj4mom-stdout.txt
	/tmp/tmpd0ii4fo_/8schools-202009110125-3-cbn8wxph-stdout.txt
	/tmp/tmpd0ii4fo_/8schools-202009110125-4-h_5980t6-stdout.txt
deleting tmpfiles dir: /tmp/tmpd0ii4fo_
done

Pour plus de détails sur l'utilisation de CmdStanPy, voir Document officiel.

annexe: comparaison de vitesse avec PyStan

Je vais également enregistrer brièvement la comparaison de vitesse avec PyStan. Tous les fichiers stan sont communs à 8schools.stan écrits dans la section" Exécution ".

CmdStanPy

L'environnement Docker est décrit dans "Création d'un environnement avec Docker". J'ai utilisé le fichier python suivant:

test-cmdstanpy.py


from cmdstanpy import CmdStanModel
import time

print("Compile started")
t1 = time.time()
model = CmdStanModel(stan_file="8schools.stan")
t2 = time.time()

data = "8schools.data.json"
print("Sampling started")
t3 = time.time()
fit = model.sample(data=data)
t4 = time.time()

print("Compile time :", t2 - t1, "seconds")
print("Sampling time :", t4 - t3, "seconds")

PyStan

Le Dockerfile utilisé est le suivant:

Dockerfile


FROM ubuntu:20.04

RUN apt-get -y update
RUN apt-get -y install python3
RUN apt-get -y install python3-pip
RUN pip3 install --upgrade pip
RUN pip3 install pystan

WORKDIR /workdir

Construisez et démarrez de la même manière que "Créer un environnement avec Docker". En outre, le fichier python utilisait ce qui suit. ::

test-pystan.py


import pystan
import time

schools_dat = {'J': 8,
               'y': [28,  8, -3,  7, -1,  1, 18, 12],
               'sigma': [15, 10, 16, 11,  9, 11, 10, 18]}

print("Compile started")
t1 = time.time()
sm = pystan.StanModel(file='8schools.stan')
t2 = time.time()
print("Sampling started")
t3 = time.time()
fit = sm.sampling(data=schools_dat, iter=1000, chains=4)
t4 = time.time()

print("Compile time :", t2 - t1, "seconds")
print("Sampling time :", t4 - t3, "seconds")

résultat

CmdStanPy

Compile time : 12.916020393371582 seconds
Sampling time : 0.16101527214050293 seconds

PyStan

Compile time : 98.87509870529175 seconds
Sampling time : 0.45189523696899414 seconds

Je l'ai mesuré plusieurs fois, mais quand il s'agissait de compiler le modèle, le résultat était que CmdStanPy était fondamentalement environ 7 fois plus rapide que PyStan [^ 6] [^ 7].

[^ 1]: Cependant, puisque j'utilise docker dans une atmosphère, la méthode de construction de l'environnement docker décrite ici n'est peut-être pas la meilleure. [^ 2]: Le document et la page github de PyStan ont été les premiers à apparaître dans une recherche Google pour "Python Stan". C'était (: //github.com/stan-dev/pystan). [^ 3]: Est-ce la reconnaissance que le numéro de version PyStan correspond au numéro de version Stan ...? [^ 4]: Voir https://cmdstanpy.readthedocs.io/en/latest/getting_started.html#installation pour plus de détails sur la partie qui installe CmdStanPy. [^ 5]: Téléchargé depuis la page de démarrage de PyStan. Https://pystan.readthedocs.io/en/latest/getting_started.html [^ 6]: Dans le cas de CmdStanPy, il y a une fonction sympa qui "compare l'heure de modification du fichier exe et du fichier stan, et si ce dernier est plus récent que le premier, il ne se compilera pas", donc soyez prudent lorsque vous mesurez à plusieurs reprises .. [^ 7]: Lorsque l'image de base de PyStan était définie sur ubuntu: 16.04, PyStan a également pris environ 50 secondes, mais la cause n'a pas été étudiée.

Recommended Posts

Remarque: préparez l'environnement de CmdStanPy avec docker
Préparer l'environnement d'exécution de Python3 avec Docker
Préparer l'environnement python3 avec Docker
Préparation de l'environnement d'exécution de PyTorch avec Docker Novembre 2019
jour de course des dockers (note)
Préparez l'environnement de développement avec anyenv
[Note] Exportez le html du site avec python.
Préparer l'environnement de Chainer sur l'instance spot EC2 avec AWS Lambda
L'histoire du partage de l'environnement pyenv avec plusieurs utilisateurs
Exemple d'environnement pytest pour réparer la base de données avec Docker
Installez Ubuntu 20.04 avec GUI et préparez l'environnement de développement
Spécifiez le nom du projet de docker-compose avec l'intégration Docker de Pycharm
Unifier l'environnement de l'équipe de développement Python en commençant par Poetry
Obtenez le nom d'hôte du PC hôte avec Docker sous Linux
Préparer l'environnement pipenv avec Amazon Linux 2
Construire un environnement Mysql + Python avec docker
Configurer un environnement de développement Python avec Atom
Reconstruisez l'environnement de développement de Django avec Docker! !! !! !!
Préparer l'environnement pour Atom pour Pythonista
(Remarque) Remarques sur la création de l'environnement TensorFlow + Flask + Nginx avec Docker Compose
Construction d'environnement Postgres avec Docker J'ai eu un peu de mal, alors notez
Préparez un environnement de test de charge distribué avec l'outil de test de charge Python Locust
Consigner périodiquement les valeurs des capteurs d'environnement Omron avec Raspberry Pi
Accéder à l'API Docker Remote avec des requêtes
J'ai vérifié le contenu du volume du docker
Exécutez IDCF Cloud CLI sur Docker
Créer un environnement Jupyter Lab (Python) avec Docker
Alignez la taille de la barre de couleurs avec matplotlib
(Remarque) Remarques sur la création d'un environnement Tensor Flow avec Docker Compose (un seul conteneur)
Derrière le flyer: utiliser Docker avec Python
Remarques lors de la création d'un environnement avec python
Vérifier l'existence du fichier avec python
À propos de l'environnement virtuel de Python version 3.7
Obtenez un environnement local pour DynamoDB avec Docker
Créer un environnement d'exécution pour Jupyter Lab
Créer un environnement Python + uWSGI + Nginx avec Docker
J'ai défini des variables d'environnement dans Docker et je les ai affichées en Python.
Préparer un environnement pour toucher les fichiers au format grib2 avec python (édition Docker)
Essayez de préparer chaque environnement de kivy
La troisième nuit de la boucle avec pour
[Linux] Créer un environnement Jenkins avec Docker
Préparer l'environnement de développement pour keyhac pour Mac
Environnement de lancement avec LineBot + Heroku + Docker + Python
La deuxième nuit de la boucle avec pour
Enregistrement des valeurs du capteur d'environnement Omron avec Raspberry Pi (type USB)
Note Python: le rôle secret de Kamma
Compter le nombre de caractères avec écho
Construire un environnement de NGINX + NGINX Unit + MySQL avec Docker
[Linux] Construction de l'environnement Docker avec Amazon Linux 2
Préparez l'environnement pour le livre O'Reilly "Deep Learning from scratch" avec apt-get (Debian 8)
J'ai installé Pygame avec Python 3.5.1 dans l'environnement de pyenv sur OS X
Remarque: Comment obtenir le dernier jour du mois avec python (ajouté le premier jour du mois)
Notez que le calcul de la corrélation moyenne par paire était très facile avec les pandas
L'histoire de l'apprentissage profond avec TPU
Hello World avec gRPC / go dans l'environnement Docker
Introduction à Python Préparons l'environnement de développement
Construire un environnement d'analyse avec Docker (jupyter notebook + PostgreSQL)