solveur python python

Oct 08 2020

J'ai écrit un programme qui lit un fichier csv contenant 100 lignes qui ressemblent à:

1;S****L;SCHOOL
2;*A*G*A*;HANGMAN

puis essayez de deviner les lettres comme dans un jeu du pendu. Mon objectif est de compter toutes les bonnes et mauvaises lettres, puis de les résumer. Le code fonctionne bien, j'obtiens environ 1670 bonnes + mauvaises tentatives pour deviner les lettres. Mon approche était de créer un dictionnaire dans lequel je stockais toutes les lettres de l'alphabet et lisais tous les mots du fichier, puis additionnais toutes les apparences d'une lettre et les stockais dans le dictionnaire. Quelque chose comme

{
   "A" : 30,
   "B" : 40
}

Ensuite, je trie le dict en fonction de chaque occurrence de lettre et j'essaie d'abord de deviner la lettre avec le plus d'apparence.

Ma question. Est-ce que je peux améliorer quelque chose pour obtenir un plus petit nombre de tentatives?

import csv

INPUT_FILE = "words.csv"


def oppenFile():        # function to read the file
    with open(INPUT_FILE, "r", encoding="utf-8") as words:
        reader = list(csv.reader(words, delimiter=";"))
        return reader


def letterCount():      # function that count every the letter in the file and return a dict: {A : 2}
    letters = dict.fromkeys("QWERTYUIOPĂÎASDFGHJKLȘȚÂZXCVBNM", 0)
    words = oppenFile()
    for w in range(len(words)):
        for l in list(words[w][2]):
            if l not in list(words[w][1]):
                letters[l] += 1
    return letters


def checkLetters(word, wholeWord, letters):     # function that solve a word return the number of right + wrong attempts
    attempts = 0
    for letter, key in letters.items():
        if letter in wholeWord and letter not in word:
            attempts += 1
            index = [i for i, lit in enumerate(wholeWord) if lit == letter]
            letters[letter] -= len(index)
            for j in range(len(index)):
                word = word[:index[j]] + letter + word[(index[j] + 1):]

        elif '*' not in word:
            break
        else:
            attempts += 1
    return attempts


def hangman():
    words = oppenFile()
    numberOfAttempts = 0
    letters = letterCount()

    for i in range(len(words)):
        letters = dict(sorted(letters.items(), key=lambda x: x[1], reverse=True)) # sort the dict

        numberOfAttempts += checkLetters(words[i][1], words[i][2], letters)

    print(f"{numberOfAttempts} right + wrong attempts")


if __name__ == "__main__":
    hangman()

Réponses

5 hjpotter92 Oct 08 2020 at 04:07

Bienvenue dans Code Review!

PEP-8

En python, il est courant (et recommandé) de suivre le guide de style PEP-8 pour écrire du code propre, maintenable et cohérent.

Les fonctions et les variables doivent être nommées dans a lower_snake_case, classes as UpperCamelCaseet constantes as UPPER_SNAKE_CASE.

Indication de type

Avec les nouvelles versions de python, vous pouvez utiliser l'indication de type pour donner un bref aperçu du type de variables et de paramètres de fonction.

Compter les lettres

Python fournit un outil intégré collections.Counterque vous pouvez utiliser.

commentaires

Les commentaires n'aident pas vraiment ici. Préférez également l'écriture de docstring plutôt que les commentaires pour les fonctions.

Noms de variables

Vous ouvrez un fichier et nommez son pointeur comme words, tandis que la fonction renvoie une liste de mots; appelé reader, qui à son tour est stocké dans une variable appelée words?

Conversions étranges

Vous générez un mappage des lettres avec leurs nombres respectifs, sous forme de dictionnaire (hash-map / table / lookup), puis convertissez-le en liste de tuple à 2 valeurs, triez-le et reconvertissez-le en dictionnaire. Pourquoi? dicta \$ O(1) \$ la recherche et le tri n'ont aucun sens dans votre cas.

Itération avec index

Vous utilisez la structure de boucle suivante:

for i in range(len(words)):

où, ien soi, ne sert à rien. Chaque occurrence d'utilisation de iest de la forme words[i]. Vous pouvez simplement parcourir les valeurs de la wordsliste elle-même:

for word in words: