Sur un A* aux points positifs, oui, tu peu éviter le centre. En revanche, non, le hasard n'est pas nécessairement le reflet d'un "mauvais algo", dans certains cas, les méthodes type Monte-Carlo sont parfaitement efficace (car le calcul exhaustif, justement, est trop lourd). Dans le cas présent, ce "tirage au hasard" peut de toute façon se remplacer par "partir de la case au points [distance eulérienne à la cible par exemple] le plus faible". De toute façon, tant que tu restes dans la zone de départ, tu n'enregistre pas les cases par lesquelles tu passes.
Je ne vois pas l'intérêt de toucher au poids des cases adjacente à ta zone de départ?!
Tu utilises une implémentation de l'A* qui est construite sur ce modèle Point-Point. L'algo A* en lui-même est plus vaste que cette implé. Si tu veux utiliser quand même cette implé sans mettre le nez dedans (perso, je pense qu'alors tu devrais regarder directement dans les SDK, parce qu'ils te fournissent ce qu'il faut pour aller d'un point à l'autre et ils se démerdent pour piocher le bon algo, cf Neoaxis qui l'a implémenté il y a quelques années et probablement Unity), alors le problème devient totalement différent. Tu ne veux pas "comment faire un A* d'un point à une zone? D'une zone à un point? D'une zone à une zone?" mais "en utilisant un algo A* Point-Point, comment puis-je faire un A* Zone-Point, Point-Zone, et Zone-Zone? (sans traiter chaque pair de points)".
Dans ce cas, le plus simple, c'est justement de piocher 2 cases au hasard des zones de départ et d'arrivée, de lancer l'implé de ton algo, de supprimer tous les points dans la zone de départ (sauf 1) par lesquels le chemin est passé et de supprimer tous les points dans la zone d'arrivée (sauf 1) de la liste de points que l'implé t'as retournée, et de réitérer l'opération pour toutes les cases de la zone de départ (sauf celles que t'as déjà traité, et celles que t'as déjà retirées).
Tu peux sinon te fixer un nombre d'itérations, et le faire de manière probabiliste (après N essais, tu pioche le meilleur résultat). Ce "hasard" pouvant également être orienté (de même que le caractère exhaustif précédent a été orienté en ignorant le cases déjà traitées).
Edit:
Autre possibilité, tu pars du points de poids de plus faible dans ta zone de départ (ie: distance eulérienne à ta zone d'arrivée), t'obtiens un chemin A-B
Ensuite, tu modifies les poids de tous les noeuds de ta grille (ou ta fonction de calcul de poids) pour qu'elle ne considère non plus la distance à la zone d'arrivée, mais le minimum entre la distance à la zone d'arrivée, et (la distance à chaque chemin déjà trouvé + la distance le long de ce chemin) jusqu'à la zone d'arrivée. Et tu réitère avec chaque point de ta zone de départ (et avec B comme destination). Bon, à mon avis, c'est pas franchement plus simple (ni performant?) que juste lancer l'algo entre chaque point de la zone de départ et n'importe quel point de la zone d'arrivée (en évitant de faire plusieurs fois les mêmes points dans la zone de départ, et en le gardant que le chemin le plus court trouvé).
Je ne vois pas l'intérêt de toucher au poids des cases adjacente à ta zone de départ?!
Tu utilises une implémentation de l'A* qui est construite sur ce modèle Point-Point. L'algo A* en lui-même est plus vaste que cette implé. Si tu veux utiliser quand même cette implé sans mettre le nez dedans (perso, je pense qu'alors tu devrais regarder directement dans les SDK, parce qu'ils te fournissent ce qu'il faut pour aller d'un point à l'autre et ils se démerdent pour piocher le bon algo, cf Neoaxis qui l'a implémenté il y a quelques années et probablement Unity), alors le problème devient totalement différent. Tu ne veux pas "comment faire un A* d'un point à une zone? D'une zone à un point? D'une zone à une zone?" mais "en utilisant un algo A* Point-Point, comment puis-je faire un A* Zone-Point, Point-Zone, et Zone-Zone? (sans traiter chaque pair de points)".
Dans ce cas, le plus simple, c'est justement de piocher 2 cases au hasard des zones de départ et d'arrivée, de lancer l'implé de ton algo, de supprimer tous les points dans la zone de départ (sauf 1) par lesquels le chemin est passé et de supprimer tous les points dans la zone d'arrivée (sauf 1) de la liste de points que l'implé t'as retournée, et de réitérer l'opération pour toutes les cases de la zone de départ (sauf celles que t'as déjà traité, et celles que t'as déjà retirées).
Tu peux sinon te fixer un nombre d'itérations, et le faire de manière probabiliste (après N essais, tu pioche le meilleur résultat). Ce "hasard" pouvant également être orienté (de même que le caractère exhaustif précédent a été orienté en ignorant le cases déjà traitées).
Edit:
Autre possibilité, tu pars du points de poids de plus faible dans ta zone de départ (ie: distance eulérienne à ta zone d'arrivée), t'obtiens un chemin A-B
Ensuite, tu modifies les poids de tous les noeuds de ta grille (ou ta fonction de calcul de poids) pour qu'elle ne considère non plus la distance à la zone d'arrivée, mais le minimum entre la distance à la zone d'arrivée, et (la distance à chaque chemin déjà trouvé + la distance le long de ce chemin) jusqu'à la zone d'arrivée. Et tu réitère avec chaque point de ta zone de départ (et avec B comme destination). Bon, à mon avis, c'est pas franchement plus simple (ni performant?) que juste lancer l'algo entre chaque point de la zone de départ et n'importe quel point de la zone d'arrivée (en évitant de faire plusieurs fois les mêmes points dans la zone de départ, et en le gardant que le chemin le plus court trouvé).
Code :
Tant qu'il existe un point P non-traité de la zone de départ
Lancer ton A* entre P et un point quelconque de la zone d'arrivée (le plus proche de ta zone de départ par exemple)
Considérer tous les points du chemin C trouvé qui sont dans la zone de départ comme "traité"
Recommencer
Retirer de chaque chemin de C tous les points de la zone d'arrivée, sauf 1 (le premier sur lequel le chemin C a tapé)
Garder le chemin de longueur minimale parmi tous les chemins trouvés