
Les grands ensembles de points contre de grands polygones signifiaient autrefois « revenez demain ». Avec CuSpatial, vous pouvez exécuter ces jointures en quelques minutes, si votre stack est correctement configuré. Ce guide montre un chemin propre, ainsi que du code que vous pouvez coller.
Sur les locataires du GPU, votre tâche s'exécute à l'intérieur d'une image. Deux bonnes options :
A) Utilisez une image RAPIDS (la plus rapide)
<24.xx>docker.io/rapidsai/rapidsai : -cuda12-runtime-ubuntu22.04-py3.10NVIDIA Visible_Devices = TousNVIDIA Driver_Capabilities=Calcul, utilitaireB) Utilisez un modèle CUDA et installez RAPIDS avec micromamba
# une seule fois dans une nouvelle instance
curl -Ls https://micro.mamba.pm/api/micromamba/linux-64/latest | tar -xvj bin/micromamba
mkdir -p ~/micromamba &&. /bin/micromamba shell init -s bash -p ~/micromamba
source ~/.bashrc
micromamba create -y -n rapids -c rapidsai -c conda-forge rapids=24.* python=3,10
micromamba active les rapides
python -c « import cudf, cuspatial ; print (cudf) ». __version__, cuspatial. __version__) »
L'un ou l'autre chemin vous donne brassard + cuspatial avec l'espace utilisateur CUDA prêt. Le pilote hôte est généralement fourni par votre fournisseur de services informatiques.
Cela montre l'API en mémoire avec un polygone jouet. Échangez les données réelles plus tard.
brassard d'importation
importation de cupy en tant que tasse
importation cuspatial
Nombre de points (N x 2)
N = 1 000_000
points = CUDF.DataFrame ({
« x » : cp.random.random (N),
« y » : cp.random.random (N),
})
# Un polygone carré (anneau fermé)
poly_offsets = CUDF.series ([0], dtype="int32")
ring_offsets = CUDF.series ([0], dtype="int32")
poly_x = CUDF.series ([0, 1, 1, 0, 0], dtype="float64")
poly_y = CUDF.series ([0, 0, 1, 1, 0], dtype="float64")
masque = cuspatial.point_in_polygon (
points ["x"], points ["y"],
poly_offsets, ring_offsets,
poly_x, poly_y,
)
# mask est un DataFrame bool (rows=points, cols=polygones)
intérieur = points [mask.iloc [:, 0]]
impression (lentille (intérieur))
Remarques
masque comporte une colonne par polygone. Utiliser .any (axis=1) si vous vous souciez seulement de savoir si un point est perdu n'importe quel polygone.Les charges de travail réelles utilisent des milliers de polygones et des centaines de millions de points. Testez moins de candidats en filtrant d'abord à l'aide de cadres de sélection, puis appelez point_dans_polygone juste sur ceux-là.
manchette d'importation, tasse en forme de tasse, couspatial
# Supposons que les points et les polygones sont déjà chargés en tant que cudf
# Exemple de structure polygonale (polys multiples, anneaux) :
# poly_offsets, poly_points_x, poly_points_y
# 1) Créez des cadres de délimitation de polygones (minx, maxx, miny, maxy)
boîtes = cuspatial.polygon_bounding_boxes (
poly_offsets, poly_offsets, poly_x, poly_y
)
# cases : DataFrame [min_x, min_y, max_x, max_y]
# 2) Filtre rapide des candidats : points dans n'importe quelle case
deuxième = (
(points.x >= boxes.min_x.min ()) & (points.x <= boxes.max_x.max ()) et
(points.y >= boxes.min_y.min ()) & (points.y <= boxes.max_y.max ())
)
pts_cand = points [seconde]
# 3) Test exact uniquement sur les candidats
masque = cuspatial.point_in_polygon (
pts_cand.x, pts_cand.y,
poly_offsets, poly_offsets, poly_x, poly_y
)
any_hit = masque.any (axis=1)
joint = pts_cand [any_hit]
Pourquoi cela aide
Le filtrage Bounding‑box réduit le nombre de tests PIP coûteux. Pour les échelles extrêmes, consultez les utilitaires quadtree de CuSpatial pour élaguer encore plus les candidats.
brassard d'importation
points = cudf.read_parquet (« sensors_utm.parquet ») # colonnes : x, y, id
poly = cudf.read_parquet (« zones_utm.parquet ») # stocké sous forme d'anneaux éclatés
# Construire des tableaux de polygones attendus par CuSpatial
poly_offsets = poly ["poly_offset"] .astype (« int32")
ring_offsets = poly ["ring_offset"] .astype (« int32")
poly_x = poly ["x"] .astype (« float64")
poly_y = poly ["y"] .astype (« float64")
Si vos polygones se trouvent dans des fichiers de formes, convertissez-les une fois en GeoParquet (hors GPU, c'est bien) pour accélérer les futurs chargements.
Pour les ensembles de données qui ne rentrent pas dans un seul GPU, utilisez Dask pour partitionner le travail. Motif :
Le code reflète la version à GPU unique mais enveloppe les DataFrames cuDF dans Dask CuDF.
Faites en sorte que ce soit ennuyeux et comparable.
entrées : N_points, N_polygones, sommets de polygones, CRS, précision
matériel : modèle GPU/VRAM, CUDA, pilote
code : version CUSpatial, chemin de code exact (avec/sans filtre)
métriques : secondes pour charger → filtre → PIP, pic de VRAM
Calculer coût par million de points:
coût_per_million = (prix_par_heure × wall_secondes/3600)/(N_points/1e6)
nvidia-smi. S'il est presque plein, découpez le tableau des points.Erreur CUDA/pas de GPU
Vérifiez nvidia-smi à l'intérieur du conteneur. Assurez-vous que votre image est prête pour CUDA et que vous définissez les variables d'environnement NVIDIA.
MemoryError ou OOM
Divisez le tableau de points ; filtrez tôt avec des bboxes ; réduisez le jeu de colonnes.
Des résultats erronés
CRS non apparié. Reprojetez et testez à nouveau. Confirmez l'orientation de l'anneau et les polygones fermés.
Charges lentes
Déplacez les données vers le NVMe local ; passez à GeoParquet ; augmentez la taille du groupe de lignes Parquet.
matériel :
processeur graphique : « <model>(<VRAM>Go) »
chauffeur : « <NVIDIA driver>»
<CUDA version>cuda : « »
logiciel :
<24.xx>image : « rapidsai/rapidsai : -cuda12-runtime-ubuntu22.04-py3.10"
python : « 3,10 »
bibliothèques :
<version>- manchette : « »
<version>- spatial : « »
entrées :
points : « s3://…/sensors_utm.parquet (N=<... >) »
polygones : « s3://…/zones_utm.parquet (polys=<... >) »
courir :
script : « pip_join.py »
remarques : « filtre bbox → PIP ; CRS=EPSG:32633"
sorties :
wall_seconds : « <... > »
coût_par_million : « <... > »
Démarrez une instance GPU avec un modèle compatible CUDA (par exemple, Ubuntu 24.04 LTS/CUDA 12.6) ou votre propre image GROMACS. Profitez d'une facturation flexible à la seconde avec modèles personnalisés et la possibilité de démarrer, d'arrêter et de reprendre vos sessions à tout moment. Vous n'êtes pas sûr des exigences du FP64 ? Contactez le support pour vous aider à sélectionner le profil matériel le mieux adapté à vos besoins informatiques.