python - ajout au même fichier à partir de plusieurs threads
Je suis en train d'écrire une application qui ajoute des lignes d'un même fichier à partir de plusieurs threads.
J'ai un problème dans lequel certaines lignes sont ajoutées sans une nouvelle ligne.
Aucune solution pour cela?
class PathThread(threading.Thread):
def __init__(self, queue):
threading.Thread.__init__(self)
self.queue = queue
def printfiles(self, p):
for path, dirs, files in os.walk(p):
for f in files:
print(f, file=output)
def run(self):
while True:
path = self.queue.get()
self.printfiles(path)
self.queue.task_done()
pathqueue = Queue.Queue()
paths = getThisFromSomeWhere()
output = codecs.open('file', 'a')
# spawn threads
for i in range(0, 5):
t = PathThread(pathqueue)
t.setDaemon(True)
t.start()
# add paths to queue
for path in paths:
pathqueue.put(path)
# wait for queue to get empty
pathqueue.join()
source d'informationauteur user1251654 | 2012-08-16
Vous devez vous connecter pour publier un commentaire.
La solution est d'écrire dans le fichier dans un seul thread.
le fait que vous ne verrez jamais pêle-texte sur la même ligne ou de nouvelles lignes dans le milieu d'une ligne est un indice que vous avez réellement n'avez pas besoin de synchroniser ajoutant dans le fichier. le problème est que vous utilisez l'impression d'écrire à un seul descripteur de fichier. je soupçonne
print
est en train de faire 2 opérations pour le descripteur de fichier en un seul appel et ces opérations sont en compétition entre les threads. fondamentalementprint
est en train de faire quelque chose comme:et parce que les différents threads de le faire simultanément sur le même descripteur de fichier parfois un thread va obtenir dans le premier à écrire et l'autre thread va obtenir alors que dans son premier à écrire et ensuite, vous aurez deux retours chariot dans une rangée. ou vraiment toute permutation de ces.
la façon la plus simple de contourner ce problème consiste à cesser d'utiliser
print
et il suffit d'utiliserwrite
directement. essayez quelque chose comme ceci:cela semble encore un danger pour moi. im pas sûr de ce que gaurantees vous pouvez vous attendre avec tous les threads en utilisant le même descripteur de fichier de l'objet et de la lutte pour la mémoire tampon interne. personnellement id pas de côté l'ensemble de la question et demandez à chaque thread a son propre descripteur de fichier. notez également que cela fonctionne parce que le défaut de la mémoire tampon d'écriture bouffées de chaleur est la ligne de tampon, de sorte que quand il fait une couleur pour le fichier, il se termine sur une
os.linesep
. pour forcer l'utilisation de la ligne de tampon envoyer un1
comme troisième argument deopen
. vous pouvez le tester comme ceci:La sortie ressemble à ceci:
Et peut-être plus des sauts de ligne où ils ne devraient pas l'être ?
vous devriez avoir à l'esprit le fait que le partage de la ressource ne doit pas être consulté par plus d'un thread à un moment ou sinon des conséquences imprévisibles peuvent se produire. ( il est appelé à l'aide des 'opérations atomiques" alors que l'utilisation de threads )
Jetez un oeil à cette page pour un peu d'intuition.
Fil De Synchronisation