سؤال

هل الثعبان تأجيل وحدة لديهم أي حماية بنيت في التأكد من العمليتين لا الكتابة إلى ملف في نفس الوقت ؟

هل كانت مفيدة؟

المحلول

للوصول لهذه الوحدة النمطية يستخدم قاعدة البيانات الأساسية الحزمة (مثل ديسيبل ، gdbm أو bsddb) .

على القيود pragraph يقول (التشديد من عندي):

على الرف وحدة لا يدعم المتزامنة القراءة/الكتابة الوصول إلى الرف الكائنات.(المتزامنة متعددة قراءة بالوصول آمنة.) عندما يكون برنامج الرف المفتوح عن كتابة أي برنامج آخر يجب أن يكون مفتوحا على القراءة أو الكتابة.Unix قفل ملف يمكن استخدامها لحل هذا ، ولكن هذا يختلف عبر إصدارات Unix و يتطلب المعرفة عن بيانات تنفيذ المستخدمة.

الخلاصة:هذا يعتمد على نظام التشغيل الأساسية ديسيبل.للحفاظ على الأشياء المحمولة ، لا بناء على التزامن.

نصائح أخرى

وكما في الإجابة الأولى، انها ليست آمنة أن يكون الكتاب متعددة إلى الرف. توجهي لجعل الرفوف أكثر أمنا لكتابة مجمع الذي يرعى افتتاح والوصول إلى الرف العناصر. رمز المجمع يبدو شيئا من هذا القبيل:

def open(self, mode=READONLY):
    if mode is READWRITE:
        lockfilemode = "a" 
        lockmode = LOCK_EX
        shelve_mode = 'c'
    else:
        lockfilemode = "r"
        lockmode = LOCK_SH
        shelve_mode = 'r'
    self.lockfd = open(shelvefile+".lck", lockfilemode)
    fcntl.flock(self.lockfd.fileno(), lockmode | LOCK_NB)
    self.shelve = shelve.open(shelvefile, flag=shelve_mode, protocol=pickle.HIGHEST_PROTOCOL))
def close(self):
    self.shelve.close()
    fcntl.flock(self.lockfd.fileno(), LOCK_UN)
    lockfd.close()

ولقد نفذت نهج ايفو ل كمدير السياق، على أي شخص مهتم:

from contextlib import contextmanager, closing
from fcntl import flock, LOCK_SH, LOCK_EX, LOCK_UN
import shelve

@contextmanager
def locking(lock_path, lock_mode):
    with open(lock_path, 'w') as lock:
        flock(lock.fileno(), lock_mode) # block until lock is acquired
        try:
            yield
        finally:
            flock(lock.fileno(), LOCK_UN) # release

class DBManager(object):
    def __init__(self, db_path):
        self.db_path = db_path

    def read(self):
        with locking("%s.lock" % self.db_path, LOCK_SH):
            with closing(shelve.open(self.db_path, "c", 2)) as db:
                return dict(db)

    def cas(self, old_db, new_db):
        with locking("%s.lock" % self.db_path, LOCK_EX):
            with closing(shelve.open(self.db_path, "c", 2)) as db:
                if old_db != dict(db):
                    return False
                db.clear()
                db.update(new_db)
                return True
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top