J'exécute Python 2.6.1 sous Windows XP SP3. Mon IDE est PyCharm 1.0-Beta 2 build PY) -96,1055.
Je stocke mes fichiers .py dans un répertoire nommé "src"; il a un __init__.py
fichier vide à l'exception d'un "__author__
"attribut en haut.
L'un d'eux s'appelle Matrix.py:
#!/usr/bin/env python
"""
"Core Python Programming" chapter 6.
A simple Matrix class that allows addition and multiplication
"""
__author__ = 'Michael'
__credits__ = []
__version__ = "1.0"
__maintainer__ = "Michael"
__status__ = "Development"
class Matrix(object):
"""
exercise 6.16: MxN matrix addition and multiplication
"""
def __init__(self, rows, cols, values = []):
self.rows = rows
self.cols = cols
self.matrix = values
def show(self):
""" display matrix"""
print '['
for i in range(0, self.rows):
print '(',
for j in range(0, self.cols-1):
print self.matrix[i][j], ',',
print self.matrix[i][self.cols-1], ')'
print ']'
def get(self, row, col):
return self.matrix[row][col]
def set(self, row, col, value):
self.matrix[row][col] = value
def rows(self):
return self.rows
def cols(self):
return self.cols
def add(self, other):
result = []
for i in range(0, self.rows):
row = []
for j in range(0, self.cols):
row.append(self.matrix[i][j] + other.get(i, j))
result.append(row)
return Matrix(self.rows, self.cols, result)
def mul(self, other):
result = []
for i in range(0, self.rows):
row = []
for j in range(0, other.cols):
sum = 0
for k in range(0, self.cols):
sum += self.matrix[i][k]*other.get(k,j)
row.append(sum)
result.append(row)
return Matrix(self.rows, other.cols, result)
def __cmp__(self, other):
"""
deep equals between two matricies
first check rows, then cols, then values
"""
if self.rows != other.rows:
return self.rows.cmp(other.rows)
if self.cols != other.cols:
return self.cols.cmp(other.cols)
for i in range(0, self.rows):
for j in range(0, self.cols):
if self.matrix[i][j] != other.get(i,j):
return self.matrix[i][j] == (other.get(i,j))
return True # if you get here, it means size and values are equal
if __name__ == '__main__':
a = Matrix(3, 3, [[1, 2, 3], [4, 5, 6], [7, 8, 9]])
b = Matrix(3, 3, [[6, 5, 4], [1, 1, 1], [2, 1, 0]])
c = Matrix(3, 3, [[2, 0, 0], [0, 2, 0], [0, 0, 2]])
a.show()
b.show()
c.show()
a.add(b).show()
a.mul(c).show()
J'ai créé un nouveau répertoire nommé "test" qui a également un __init__.py
fichier vide à l'exception d'un "__author__
"en haut. J'ai créé un MatrixTest.py pour unir ma classe Matrix:
#!/usr/bin/env python
"""
Unit test case for Matrix class
See http://jaynes.colorado.edu/PythonGuidelines.html#module_formatting for Python coding guidelines
"""
import unittest #use my unittestfp instead for floating point
from src import Matrix # Matrix class to be tested
__author__ = 'Michael'
__credits__ = []
__license__ = "GPL"
__version__ = "1.0"
__maintainer__ = "Michael"
__status__ = "Development"
class MatrixTest(unittest.TestCase):
"""Unit tests for Matrix class"""
def setUp(self):
self.a = Matrix.Matrix(3, 3, [[1, 2, 3], [4, 5, 6], [7, 8, 9]])
self.b = Matrix.Matrix(3, 3, [[6, 5, 4], [1, 1, 1], [2, 1, 0]])
self.c = Matrix.Matrix(3, 3, [[2, 0, 0], [0, 2, 0], [0, 0, 2]])
def testAdd(self):
expected = Matrix.Matrix(3, 3, [[7, 7, 7], [5, 6, 7], [9, 9, 9]]) # need to learn how to write equals for Matrix
self.a.add(self.b)
assert self.a == expected
if __name__ == '__main__': #run tests if called from command-line
suite = unittest.TestLoader().loadTestsFromTestCase(TestSequenceFunctions)
unittest.TextTestRunner(verbosity=2).run(suite)
Pourtant, lorsque j'essaie d'exécuter mon MatrixTest, j'obtiens cette erreur:
C:\Tools\Python-2.6.1\python.exe "C:/Documents and Settings/Michael/My Documents/Projects/Python/learning/core/test/MatrixTest.py"
Traceback (most recent call last):
File "C:/Documents and Settings/Michael/My Documents/Projects/Python/learning/core/test/MatrixTest.py", line 8, in <module>
from src import Matrix # Matrix class to be tested
ImportError: No module named src
Process finished with exit code 1
Tout ce que j'ai lu me dit que d'avoir le init. Py dans tous mes répertoires devrait s'en occuper.
Si quelqu'un pouvait souligner ce que j'ai manqué, je l'apprécierais beaucoup.
J'aimerais aussi des conseils sur la meilleure façon de développer et de maintenir des classes de tests source et unitaire. J'y pense comme je le fais habituellement lorsque j'écris des répertoires Java:/src et/test, avec des structures de packages identiques en dessous. Est-ce une pensée "pythonique", ou devrais-je envisager un autre schéma d'organisation?
METTRE À JOUR:
Merci à ceux qui ont répondu, voici la solution qui a fonctionné pour moi:
from src import Matrix # Matrix class to be tested
sys.path
comme variable d'environnement dans ma configuration la plus simple, avec les répertoires ./src et ./test séparés par des points-virgules.C'est un peu une supposition, mais je pense que vous devez changer votre PYTHONPATH variable d'environnement pour inclure les répertoires src et test.
L'exécution de programmes dans le répertoire src
peut avoir fonctionné, car Python insère automatiquement le répertoire du script dans lequel il s'exécute actuellement sys.path
. L'importation de modules dans src
aurait donc fonctionné tant que vous exécutez également un script qui réside dans src
.
Mais maintenant que vous exécutez un script à partir de test
, le répertoire test
est automatiquement ajouté à sys.path
, tandis que src
ne l'est pas.
Tous les répertoires répertoriés dans PYTHONPATH sont ajoutés à sys.path
et Python recherche sys.path
pour rechercher des modules.
Aussi, si vous dites
from src import Matrix
alors Matrix
ferait référence au paquet, et vous auriez besoin de dire Matrix.Matrix
pour accéder à la classe.
Concernant les meilleures pratiques, PycURL utilise un répertoire tests
au même niveau que le code source principal. D'un autre côté, les projets comme Twisted ou sorl-thumbnail utilisent un sous-répertoire test(s)
sous le code source principal.
~ unutb a déjà répondu à l'autre moitié de la question.