8
votes

Comment dessiner le plus gros polygone d'un ensemble de points

Donc, j'ai un ensemble de points (x, y), et je veux pouvoir dessiner le plus gros polygone avec ces points sous forme de sommets. Je peux utiliser des patchs.polygon () dans matplotlib, mais cela dessine simplement des lignes entre les points de l'ordre que je leur donne. Cela ne fait pas automatiquement ce que je veux. À titre d'exemple, si vous souhaitez dessiner un carré et trier les points en augmentant X, puis en augmentant Y, je n'aurai pas de carré, mais deux triangles reliant. (la ligne "traverse")

Donc, le problème est maintenant de trouver un moyen de trier la liste des points de sorte que je "tourne autour de l'extérieur" du polygone lors de l'itération de cette liste.

ou y a-t-il peut-être une autre fonctionnalité dans Matplotlib qui peut le faire pour moi?


0 commentaires

7 Réponses :


2
votes

Je ne sais pas Matplotlib, mais ce dont vous avez besoin / que vous souhaitez dessiner la coque convexe du point de point. Pensez à la coque convexe comme une corde élastique que vous placez autour du point de vue. La forme que prend la corde élastique est la coque convexe. Il existe différents algorithmes pour calculer une coque convexe, alors vérifiez si Matplotlib supporte tout. Sinon, vérifiez ces liens pour un point de départ sur la manière de la mettre en œuvre.

http://fr.wikipedia.org/wiki/convex_hull

http://en.wikipedia.org/wiki/convex_hull_algorithms


2 commentaires

Merci. Mais autant que je comprends bien, "Trouver la coque convexe" signifie normalement trouver le sous-ensemble de points faisant partie de la coque convexe de l'ensemble total.


Merci. Mais autant que je comprends bien, "Trouver la coque convexe" signifie normalement trouver le sous-ensemble de points faisant partie de la coque convexe de l'ensemble total. D'autre part, j'ai déjà la coque convexe dans certains sens, j'ai juste besoin de les commander de telle sorte que je reçois un dessin de la coque convexe lorsque je dessine des lignes entre eux.



1
votes

Ici, vous avez une implémentation python de la coque convexe (c'est ce que vous recherchez):

http://www.scipy.org/cookbook/fininding_convex_hull


1 commentaires

Le problème est que cet algorithme nécessite que j'ai plus de cinq points. J'ai besoin de quelque chose qui fonctionne pour les cas simples. C'est aussi une sorte de surkilleuse, car j'ai déjà le jeu qui est la coque convexe, j'ai juste besoin de le trier correctement pour pouvoir le dessiner.



2
votes

Si vous connaissez déjà les points de coque , puis dessinez le polygone en connectant ces points est en fait assez facile à faire dans matplotlib car les polygones sont implémentés dans Matplotlib comme les chemins . Je commencerais avec le classe matplotlib.path .

Si vous ne connaissez pas les points de la coque, je suis d'accord avec Elmar - La coque convexe est l'algorithme que vous voulez. J'ai codé cet algorithme à Numpy et le complott dans Matplotlib. Mon code a été emprunté à une excellente recette du livret de recettes Scipy, ici . Cette recette comprend une implémentation numpue et le code complet requis pour tracer dans matplotlib la coque convexe autour d'un ensemble de points donné.

En outre, Matplotlib comprend un package appelé Delauneau , qui, comme vous l'aviez peut-être deviné, c'est pour tesseler une surface à l'aide de la triangulation Delaunay. Et comme vous le savez peut-être, cela est lié à la coque convexe à travers la tesselation Voronoi - c'est-à-dire., Les limites de chaque cellule Voronoi sont créées à partir d'un calcul de coque convexe.


2 commentaires

Mais étant donné que j'ai déjà le point de pointe convexe, cela pourrait être surchargé. J'ai juste besoin de les trier afin qu'ils viennent dans le sens des aiguilles d'une montre ou dans le sens antihoraire. Et l'algorithme de votre lien ne prendra pas moins de 6 points.


Delauney est plutôt surpuissant pour trianguer un polygone convexe. Au lieu de simplement utiliser un fan de triangle. Cependant, si vous voulez trianguler, y compris les points intérieurs, utilisez Delauneau.



2
votes

De vos commentaires à d'autres réponses, vous semblez avoir déjà l'ensemble des points définissant la coque convexe, mais ils ne sont pas commandés. Le moyen le plus simple de les commander serait de prendre un point à l'intérieur de la coque convexe comme l'origine d'un nouveau cadre de coordonnées. Vous transformez ensuite les coordonnées cartésiennes (la plupart probablement) de vos points en coordonnées polaires, en ce qui concerne ce nouveau cadre. Si vous commandez vos points par rapport à leur coordonnée d'angle polaire, vous pouvez dessiner votre coque convexe. Ceci n'est valide que si l'ensemble de vos points a défini une coque convexe (non concave).


0 commentaires

2
votes

Alors, que diriez-vous de faire le tri vous-même?

Dites, le jeu de point de coque convexe est stocké sous forme de liste points en python et c est le certains Sorte de point interne dans votre ensemble de point de coque convexe, vous pouvez simplement préparer un comparateur comme le pseudo-code suivant: xxx

L'idée est de faire utiliser point produit pour comprendre la commande par leur rotation relative.


0 commentaires

4
votes

Comme suggéré, toute une solution simple est de calculer les angles d'un point interne à tous les points et de les trier.

Voici pour vous un NUMPY NUMPY CODE> fonction pour calculer CCWorder CODE>: P>

In []: A
Out[]:
array([[0, 0, 1, 1],
       [0, 1, 1, 0]])
In []: ccworder(A)
Out[]: array([0, 3, 2, 1])


1 commentaires

Pour des cas simples, c'est définitivement la voie à suivre (+1). Si les points qu'il a toujours formés une coque convexe, cela fonctionnera toujours. Cependant, vous voudrez peut-être souligner que cela ne fonctionnera pas pour des polygones plus complexes (c'est-à-dire quoi que ce soit où la commande "correcte" des points n'est pas simplement un angle croissant sur le centre).



0
votes

J'ai utilisé Sciped.Spatial pour ce type de problème. Il a des fonctions spécifiques pour tracer des coques convexes. Voir ici . Peut-être que c'est plus de puissance de feu que vous ne le vouliez.


0 commentaires