On m'a posé la question suivante dans une interview aujourd'hui et j'y pense depuis. Je n'ai pas pu y répondre et n'ai pas pu trouver de solution en ligne.
Étant donné un échiquier de dimensions X par des reines Y et N, déterminez s'il est possible d'agencer ces reines sur le plateau de sorte qu'elles ne puissent pas s'attaquer.
Une carte 2 x 3 avec 2 reines a une solution, donc l'algorithme retournerait vrai:
Q . .
. . Q
Je recherche une approche de programmation pour ce puzzle, pas seulement des moyens de le résoudre sur papier, par exemple.
algorithms
puzzles
chess
Interviewé
la source
la source
Réponses:
Ce n'est pas (IMO) un problème très intéressant du point de vue de la programmation. Vous pouvez trouver un algorithme récursif qui essaie tous les arrangements, quelque chose comme ceci:
Si vous pensez un peu au problème, vous vous rendrez compte qu'il n'y a aucun moyen de placer N reines sur une planche où X <N ou Y <N car cela nécessiterait qu'au moins deux reines se retrouvent dans le même rang ou fichier, et ils s’attaqueraient donc mutuellement. Si vous lisez le problème des n-reines, vous apprendrez rapidement qu'il est toujours possible de placer N reines sur une carte NxN pour N> 3. Maintenant, nous savons que la réponse est NON pour (X <N ou Y <N) et OUI pour (X> = N et Y> = N, N> 3). Il ne reste que les cas particuliers:
Alors maintenant, notre belle fonction récursive devient une fonction simple qui compare simplement N à X et Y et renvoie un résultat standard. C'est génial du point de vue des performances, car vous pouvez obtenir une réponse en temps constant. Ce n'est pas si génial du point de vue de la programmation parce que vous vous rendez compte, à ce stade, que la question est vraiment plus sur la façon dont vous pouvez résoudre des énigmes que sur votre capacité à écrire une fonction récursive.
(Et garçon oh garçon, j'espère vraiment que je n'ai pas fait une erreur stupide dans ma réponse de smarty-pants. ;-)
la source
That's great from a performance point of view, since you can get an answer in constant time. It's not so great from a programming point of view because you realize, at this point, that the question is really more about how well you can solve puzzles than it is about your ability to write a recursive function.
En fait, je pense que l'intervieweur attendait cette solution O (1) car elle est finalement meilleure et pas évidente pour beaucoup de gens. Le problème de la reine nxn est dans tous les cours de programmation comme un exercice de récursivité - beaucoup de gens ne réfléchiront pas plus profondément en revoyant ce problème.Si l'intervieweur vous avait demandé d'écrire le code du problème, je pense que ce n'est pas juste. L'algorithme nécessite du travail. Cependant, si l'idée était de montrer à l'enquêteur les classes, les méthodes ou certains concepts que vous auriez besoin d'utiliser ou quelque chose de similaire, alors cela pourrait être une bonne question.
Le problème est un problème informatique classique et est discuté dans de nombreux livres de ce type. Une excellente explication, avec animation et 12 solutions différentes avec du code peut être trouvée ici:
http://en.wikipedia.org/wiki/Eight_queens_puzzle
Le code peut également être trouvé ici: http://www.codeproject.com/KB/java/EightQueen.aspx
Ne vous sentez pas mal à ce sujet, comme je l'ai dit, ce n'est pas facile.
la source
C'est plus un commentaire vraiment, mais ça ne rentre pas dedans ...
Un échiquier a 8x8 cases, ni plus ni moins (ces questions m'ennuient toujours avec cette approche d'un échiquier personnalisé).
Mais de toute façon, si vous avez un échiquier x * y, et n reines et que la reine "prend" ces champs
pourriez-vous simplement créer un tableau bidimensionnel et "signaler" tous les champs qu'une seule reine attaque. Ensuite, placez l'autre (du milieu du plateau), marquez les champs restants, etc. jusqu'à ce que vous exécutiez l'un des champs ou des reines.
Il s'agit bien sûr d'une approche très simplifiée, car si elle était positionnée de manière incorrecte, je suppose que le nombre maximum de reines varierait.
Hmm, je viens de trouver cela aussi - 8 problèmes de reines.
la source
Fondamentalement, l'algorithme de retour arrière fonctionne comme ceci:
Créez un tableau X par Y. Réglez tous les carrés sur vide.
Réglez le nombre de reine à zéro.
Réglez votre position actuelle sur (1,1)
Voyez si vous pouvez placer une reine dans la position actuelle.
Si vous le pouvez, définissez Array (X, Y) sur queen, augmentez le nombre de reine. Si vous avez placé toute la reine, arrêtez , vous avez une solution.
Si la position actuelle n'est pas (X, Y), incrémentez la position actuelle et passez à l'étape 4.
Trouvez la reine dans la dernière position (celle qui vient en dernier dans l'ordre où vous augmentez les positions). Définissez la position actuelle sur la position de cette reine, supprimez-la et décrémentez le nombre de reine.
Si le nombre de reines est nul, arrêtez , il n'y a pas de solution.
Incrémentez la position actuelle.
Passez à l'étape 4.
la source
Ajout aux autres réponses: la création d'un tableau bidimensionnel ne fait que compliquer le code.
Vous avez juste besoin d'un vecteur de taille 8 pour un échiquier ordinaire. Ou 8 + 1 si, comme C, la 1ère position est 0, seulement pour simplifier le code, et traiter 1-8 et non 0-7.
Si vous pensez que x est votre position dans le tableau, et y le contenu de la position. Par exemple, la planche [1] = 8 signifie que la première reine est à [1,8].
De cette façon, il vous suffit de vérifier la validation des colonnes.
À la faculté, je suis tombé sur un très vieux livre (des années 60?), Sur les algorithmes implémentés dans Dartmouth BASIC, qui implémentait le problème des 8 reines en utilisant le moins de mémoire possible (étant aussi vieux, cela a du sens).
Pour autant que je m'en souvienne, il a utilisé l'idée de vecteur, et il a essentiellement forcé toutes les positions de la carte avec deux cycles FOR. Pour vérifier la validité de la position, il a utilisé une troisième boucle, un cycle WHILE dans chaque position revient dans le vecteur et vérifie un nombre égal ou une formule utilisant une opération tangente pour vérifier les diagonales.
Malheureusement, j'ai perdu la trace de ce livre ...
Cet algorithme a trouvé toutes les solutions au problème des n-queen.
la source
Si vous n'avez qu'à écrire un algorithme pour déterminer si un tel arrangement existe, alors regardez la recherche existante:
Puzzle de huit reines sur Wikipédia .
Vous pouvez renvoyer trivialement faux si N> min (X, Y).
Après avoir lu cette page, vous savez retourner vrai si N <= min (X, Y) et 2, 3! = Min (X, Y).
Ce qui laisse 2, 3 == min (X, Y) et N <= min (X, Y).
Eh bien, si N <min (X, Y), trouver une solution est trivial.
Si N == min (X, Y), il n'y a de solution que si max (X, Y)> N.
la source
Il n'y a évidemment pas de solution si N> min (X, Y). Sinon, vous pouvez facilement montrer qu'il n'y a pas de solution pour N = X = Y = 2, N = X = Y = 3. Pour tous les autres cas, il semble y avoir une solution. Le nombre de solutions semble augmenter à mesure que N croît.
Vous pouvez trouver une solution grâce à une recherche exhaustive avec retour en arrière: Mettez une reine dans la première rangée, colonne 1. Mettez une reine dans la deuxième rangée, dans la première colonne que la reine dans la rangée 1 ne peut pas atteindre. Mettez une reine dans la deuxième rangée, etc. Si une reine ne peut pas être placée dans la rangée k, alors vous la retirez et déplacez la reine dans la rangée k-1 dans la position inoccupée suivante.
la source