I'm a newb working through Learn Python the Hard Way.
The point of this exercise is to write a word scanner for that passes the nosetests when run by a provided unit test.
While running nosetests on the following provided unit test I was getting this error:
`TypeError: unbound method scan() must be called with lexicon instance as first argument (got str instance instead)
Lesson-supplied 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)])
After some investigation I found here a user who is working through the same exercise:
The answer there suggested instantiating (instaniating?) the method inside the unit test. So I did the following modification and wrote up my class in file ex48.py and it passes nosetests.
Modified Test
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')])
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
I'm not sure if the unit test was meant to be changed. I found a clue about 'directly intantiating an object' here:
Python: does calling a method 'directly' instantiate the object?
But am not sure if this applies. Can a scanner be made to instantiate itself or is the provided unit test a trick 'question' and must be modified?
2 Answers 2
In the online version of Learn Python The Hard Way they have:
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')])
for the test, which suggests that you don't need a lexicon class, but a lexicon.py file with a scan function to test.
And it's spelled instantiating (as in I'm making an instance of this class).
2 Comments
You should keep the test the way it was, and use a @staticmethod decorator on the scan method. This way, you'll be able to call the method directly from the class without need to instanciate an object for this.
class lexicon(object):
@staticmethod
def scan(data):
#do the stuff here
1 Comment
def scan(data): Thanks much. :)Explore related questions
See similar questions with these tags.