【问题标题】:python multithreading and file locking issuespython多线程和文件锁定问题
【发布时间】:2014-06-27 11:13:03
【问题描述】:

我以两种方式实现了多线程代码,但在这两种方式中都出现了错误。有人可以解释导致问题的原因吗?

在版本 1 中,我得到一个异常,说两个参数传递给 writekey 函数而不是一个。 在版本 2 中,其中一个线程读取空行,因此在处理空字符串时会引发异常。

我用的是锁,不应该防止多个线程同时访问函数或文件吗?

版本 1:

class SomeThread(threading.Thread):
    def __init__(self, somequeue, lockfile):
        threading.Thread.__init__(self)
        self.myqueue = somequeue
        self.myfilelock = lockfile

    def writekey(key):
        if os.path.exists(os.path.join('.', outfile)):
            with open(outfile, 'r') as fc:
                readkey = int(fc.readline().rstrip())
            os.remove(os.path.join('.', outfile))

        with open(outfile, 'w') as fw:
            if readkey > key:
                fw.write(str(readkey))
            else:
                fw.write(str(key))

    def run(self):
        while(True):
            dict = self.myqueue.get()

            self.myfilelock.acquire()
            try:
                self.writekey(dict.get("key"))
            finally:
                self.myfilelock.release()

            self.myqueue.task_done()

populateQueue() # populate queue with objects    
filelock = threading.Lock()

for i in range(threadnum):
    thread = SomeThread(somequeue, filelock)
    thread.setDaemon(True)
    thread.start()

somequeue.join()

版本 2:

def writekey(key):
    if os.path.exists(os.path.join('.', outfile)):
        with open(outfile, 'r') as fc:
            # do something...

        os.remove(os.path.join('.', outfile))

    with open(outfile, 'w') as fw:
        # do something...

class SomeThread(threading.Thread):
    def __init__(self, somequeue, lockfile):
        threading.Thread.__init__(self)
        self.myqueue = somequeue
        self.myfilelock = lockfile

    def run(self):
        while(True):
            dict = self.myqueue.get()

            self.myfilelock.acquire()
            try:
                writekey(dict.get("key"))
            finally:
                myfilelock.release()

            self.myqueue.task_done()

# Same as above ....

【问题讨论】:

  • 如果您能发布例外情况将会很有帮助。
  • 线程 Thread-2 中的异常:回溯(最近一次调用最后一次):...在运行 self.writekey(dict.get("key")) 文件中...,在 writekey 中 readkey = int(fc.readline().rstrip()) ValueError: int() 基数为 10 的无效文字:''

标签: python multithreading exception locking


【解决方案1】:

在版本 1 中,def writekey(key) 应以“self”作为第一个参数声明,即

def writekey(self, key):

版本 2 中的问题不太清楚。我假设在读取outfile 时正在读取一个空行。这是正常的,它表明已经到达文件结尾。通常你会跳出你的读取循环。通常最好在for 循环中逐行读取文件,例如

with open(outfile, 'r') as fc:
    for line in fc:
        # process the line

for 循环将在到达文件末尾时自然终止。

【讨论】:

  • 试过了。版本 2 出现同样的错误。我正在从文件中读取并在 writekey() 函数中将其转换为整数 (int(fc.readline().rstrip()))。异常是:线程 Thread-4 中的异常,ValueError:int() 的无效文字,基数为 10:''
  • 由于行读取为空而引发异常。但是它应该在 writekey() 函数之前编写。
  • 其实outfile只有一行,存放key。打开outfile后,读取前一个key,然后删除文件。作为参数传递的键随后被写入新创建的输出文件。
  • int('') 会引发该异常。不要处理空行。空行表示文件结束 - 没有数据供您处理。您没有显示该代码,因此我们无法判断发生了什么。此外,没有必要删除文件 - open(outfile, 'w') 将截断现有文件,否则它将创建它。
  • 我在 writekey() 函数内部进行了编辑。当我检查文件时,里面什么都没有。应该总是有一条带钥匙的线。这怎么可能发生?我会在不删除文件的情况下尝试它。
猜你喜欢
  • 2020-08-28
  • 2016-01-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-09-19
  • 2018-07-28
相关资源
最近更新 更多