Marten Lienen, David Lüdke, Jan Hansen-Palmus, Stephan Günnemann

Ce référentiel contient le code utilisé pour produire les résultats dans notre article: OpenReview, Arxiv.
Outre le modèle, le chargement des données et le code de formation, ce référentiel contient également du code pour configurer et exécuter OpenFoam et reproduire ses sorties. Ces outils pourraient être un point de départ extrêmement utile pour d'autres chercheurs dans le domaine. En particulier, il y a
# Clone the repository
git clone https://github.com/martenlienen/generative-turbulence.git
# Change into the repository
cd generative-turbulence
# Install package editably with dependencies
pip install -e .
# If you need a specific pytorch version, e.g. CPU-only or an older CUDA version, check
#
# https://pytorch.org/get-started/locally/
#
# and run, for example,
#
# pip install torch --extra-index-url https://download.pytorch.org/whl/cu117
#
# before installing this package. L'ensemble de données Shapes est hébergé à la bibliothèque de l'Université TUM. Pour le télécharger, suivez les instructions sur leur page ou exécutez les étapes suivantes. Tout d'abord, téléchargez les fichiers.
# Download all archives to data/shapes/download
scripts/download-dataset.sh Notez que cela peut prendre beaucoup de temps car les données traitées sont à environ 2 To. Le script utilise rsync , vous pouvez donc reprendre des téléchargements partiels. Si vous souhaitez également télécharger les données de cas OpenFoam brutes, exécutez à la place
scripts/download-dataset.sh --with-rawAprès avoir téléchargé les archives Invididuales, vous devez extraire les fichiers. Le script suivant le fait pour vous
scripts/extract-dataset.shEnsuite, vous pouvez commencer à former le modèle comme décrit ci-dessous.
L'extrait suivant charge les données de l'un des fichiers data.h5 dans l'ensemble de données pour que vous puissiez explorer et expérimenter.
import numpy as np
import h5py as h5
def load_data ( path , idx , features = [ "u" , "p" ]):
"""Load data from a data.h5 file into an easily digestible matrix format.
Arguments
---------
path
Path to a data.h5 file in the `shapes` dataset
idx
Index or indices of sample to load. Can be a number, list, boolean mask or a slice.
features
Features to load. By default loads only velocity and pressure but you can also
access the LES specific k and nut variables.
Returns
-------
t: np.ndarray of shape T
Time steps of the loaded data frames
data_3d: np.ndarray of shape T x W x H x D x F
3D data with all features concatenated in the order that they are requested, i.e.
in the default case the first 3 features will be the velocity vector and the fourth
will be the pressure
inside_mask: np.ndarray of shape W x H x D
Boolean mask that marks the inside cells of the domain, i.e. cells that are not part
of walls, inlets or outlets
boundary_masks: dict of str to nd.ndarray of shape W x H x D
Masks that mark cells belonging to each type of boundary
boundary_values: dict[str, dict[str, np.ndarray]]
Prescribed values for variables and boundaries with Dirichlet boundary conditions
"""
with h5 . File ( path , mode = "r" ) as f :
t = np . array ( f [ "data/times" ])
cell_data = np . concatenate ([ np . atleast_3d ( f [ "data" ][ name ][ idx ]) for name in features ], axis = - 1 )
padded_cell_counts = np . array ( f [ "grid/cell_counts" ])
cell_idx = np . array ( f [ "grid/cell_idx" ])
n_steps , n_features = cell_data . shape [ 0 ], cell_data . shape [ - 1 ]
data_3d = np . zeros (( n_steps , * padded_cell_counts , n_features ))
data_3d . reshape (( n_steps , - 1 , n_features ))[:, cell_idx ] = cell_data
inside_mask = np . zeros ( padded_cell_counts , dtype = bool )
inside_mask . reshape ( - 1 )[ cell_idx ] = 1
boundary_masks = { name : np . zeros ( padded_cell_counts , dtype = bool ) for name in f [ "grid/boundaries" ]. keys ()}
for name , mask in boundary_masks . items ():
mask . reshape ( - 1 )[ np . array ( f [ "grid/boundaries" ][ name ])] = 1
boundary_values = {
ft : {
name : np . atleast_1d ( desc [ "value" ])
for name , desc in f [ "boundary-conditions" ][ ft ]. items ()
if desc . attrs [ "type" ] == "fixed-value"
}
for ft in features
}
return t , data_3d , inside_mask , boundary_masks , boundary_valuesVous pouvez l'utiliser comme
from matplotlib . pyplot import matshow
path = "data/shapes/data/2x2-large/data.h5"
t , data_3d , inside_mask , boundary_masks , boundary_values = load_data ( path , [ 50 , 300 ])
matshow ( np . linalg . norm ( data_3d [ - 1 , :, :, 20 , : 3 ], axis = - 1 ). T )
Les fichiers data.h5 contiennent plus d'informations que cet extrait de chargement. Pour explorer ce qui est disponible d'autre, perdez dans notre chargeur de données.
Pour générer des données pour de nouvelles simulations OpenFoam, assurez-vous d'abord que vous avez installé les dépendances supplémentaires et que vous avez just disponible:
pip install -e " .[data] " Si vous ne voulez pas utiliser just , vous pouvez également lire le justfile et exécuter les commandes vous-même.
Commencez par créer un conteneur Docker avec OpenFoam installé:
just of-dockerGénérez maintenant un tas de nouveaux cas. Par exemple, le suivant met en place tous les cas OpenFoam (simulations) à partir de notre ensemble de données:
./scripts/generate-shapes.py data/shapesBien sûr, vous pouvez adapter le script pour créer d'autres formes ou des ensembles de données complètement nouveaux.
Vous pouvez maintenant résoudre le boîtier (exécuter la simulation) avec OpenFoam localement
just of-solve path/to/caseOu soumettez-en tout un tas à votre propre cluster Slurm:
./scripts/solve-slurm.py data/shapes/data/ * /caseEnsuite, appliquez le post-traitement, par exemple la conversion HDF5, à chaque simulation, par exemple
just postprocess data/shapes/data/2x2Enfin, calculez les statistiques de l'ensemble de formation pour la normalisation des fonctionnalités:
./scripts/dataset-stats.py data/shapes Pour démarrer une formation, appelez train.py avec vos paramètres, par exemple
./train.py data.batch_size=128 Le script d'entraînement utilise HYDRA pour la configuration, alors consultez les fichiers du répertoire config , pour en savoir plus sur tous les paramètres disponibles.
Pour réécrire les expériences du papier, exécutez
./train.py -cn shapes_experiment -m qui commence à s'entraîner avec les paramètres de config/shapes_experiment.yaml . Si vous n'avez pas de cluster Slurm disponible, supprimez les paramètres liés au launcher .
Si vous vous appuyez sur ce travail, veuillez citer notre article comme suit.
@inproceedings{lienen2024zero,
title = {From {{Zero}} to {{Turbulence}}: {{Generative Modeling}} for {{3D Flow Simulation}}},
author = {Lienen, Marten and L{"u}dke, David and {Hansen-Palmus}, Jan and G{"u}nnemann, Stephan},
booktitle = {International {{Conference}} on {{Learning Representations}}},
year = {2024},
}