2011-07-30 4 views
2

Je suis un newb travaillant sur Learn Python the Hard Way.Appel d'une méthode en Python de manière plus efficace

Le but de cet exercice est d'écrire un analyseur de mots pour lequel passe les nosetests lorsqu'il est exécuté par un test unitaire fourni.

Lors de l'exécution nosetests sur le test unitaire prévu suivant, je recevais cette erreur:

`TypeError: analyse de la méthode non liée() doit être appelée avec instance de lexique comme premier argument (a par exemple str à la place)

Leçon fourni par test

from nose.tools import * 
from ex48 import lexicon 

def test_directions(): 
    assert_equal(lex.scan("north"), [('direction', 'north')]) 
    result = lex.scan("north south east") 
    assert_equal(result, [('direction', 'north'), 
          ('direction', 'south'), 
          ('direction', 'east)]) 

Après quelques recherches, je trouve ici un utilisateur qui travaille dans le même exercice:

nosetests, python

python variables, classes

La réponse a suggéré qu'il y instanciation (instaniating?) La méthode dans le test unitaire. J'ai donc fait la modification suivante et j'ai écrit ma classe dans le fichier ex48.py et ça passe nos questions.

test modifié

from nose.tools import * 
from ex48 import lexicon 


def test_directions(): 
    lex = lexicon("north") 
    assert_equal(lex.scan("north"), [('direction', 'north')]) 
    lex = lexicon("north south east") 
    result = lex.scan("north south east") 
    assert_equal(result, [('direction', 'north'), 
          ('direction', 'south'), 
          ('direction', 'east')]) 

de ex48.py - Scanner

class lexicon(object): 

    def __init__(self, data): 
     #nosetests fails me if I don't put in some dummy 
     # __init__ function with a dummy line, not sure why. 
    self.direction = data 

    def scan(self, data): 
     split_data = data.split() 
     directions = ['north', 'south', 'east', 'west'] 
     data_reply = [] 
     #for loop for the length of the list 
     for split_data_item in split_data: 
      #If data is in the directions list 
      if split_data_item in directions: 
       #Add [('direction', data)] to a dict 
       data_reply.append(('direction', split_data_item)) 

     #Return the list 
     return data_reply 

Je ne sais pas si le test unitaire a été conçu pour être changé. J'ai trouvé un indice sur « intantiating directement un objet » ici:

Python: does calling a method 'directly' instantiate the object?

Mais ne sais pas si cela vaut. Un scanner peut-il se faire instancier ou l'unité fournie teste-t-elle une «question» de tour et doit-elle être modifiée?

Répondre

2

Vous devez conserver le test tel quel et utiliser un décorateur @staticmethod sur la méthode de scan. De cette façon, vous serez capable d'appeler la méthode directement depuis la classe sans avoir besoin d'instancier un objet pour cela.

class lexicon(object): 

    @staticmethod 
    def scan(data): 
     #do the stuff here 
+0

Cela a fonctionné avec une petite modification: 'def scan (data):' Merci beaucoup. :) –

+0

@Steve Narrow: merci, j'ai édité ma réponse. –

4

Dans la version en ligne de Learn Python The Hard Way ils ont:

def test_directions(): 
    assert_equal(lexicon.scan("north"), [('direction', 'north')]) 
    result = lexicon.scan("north south east") 
    assert_equal(result, [('direction', 'north'), 
          ('direction', 'south'), 
          ('direction', 'east')]) 

pour le test, ce qui laisse supposer que vous n'avez pas besoin d'une classe lexique, mais un fichier lexicon.py avec une fonction de balayage à tester.

Et c'est l'instanciation orthographiée (comme dans le cas d'une instance de cette classe).

+0

Ah oui, mon mauvais là, je n'ai pas copié coller l'original, mais le modifié et supprimé les lignes supplémentaires. Je vous remercie. –

+0

Et j'ai aussi essayé cela en utilisant un fichier lexicon.py et j'ai changé l'import. Fonctionne aussi bien. Muchas. –

Questions connexes