আমি কীভাবে পাইথনে একাধিক ভেরিয়েবল সংরক্ষণ এবং পুনরুদ্ধার করব?


104

আমার একটি ফাইলে প্রায় এক ডজন বস্তু সংরক্ষণ করতে হবে এবং তারপরে সেগুলি পুনরুদ্ধার করতে হবে। আমি আচার এবং তাক সহ লুপের জন্য একটি ব্যবহার করার চেষ্টা করেছি কিন্তু এটি সঠিকভাবে কাজ করে না।

সম্পাদনা করুন।
আমি যে বস্তুগুলি সংরক্ষণ করার চেষ্টা করছিলাম সেগুলির সমস্তই একই শ্রেণিতে ছিল (আমার আগে এটি উল্লেখ করা উচিত ছিল), এবং আমি বুঝতে পারি নি যে আমি পুরো ক্লাসটিকে কেবল এটির মতো সংরক্ষণ করতে পারি:

import pickle
def saveLoad(opt):
    global calc
    if opt == "save":
        f = file(filename, 'wb')
        pickle.dump(calc, f, 2)
        f.close
        print 'data saved'
    elif opt == "load":
        f = file(filename, 'rb')
        calc = pickle.load(f)
    else:
        print 'Invalid saveLoad option'

1
আপনি বলছেন আপনি লুপের চেষ্টা করেছেন দয়া করে এই কোডটি পোস্ট করুন এবং কেন "এটি সঠিকভাবে কাজ করে না" (যেমন, কী হয়েছিল এবং আপনি কী হতে চেয়েছিলেন)।
ব্লেয়ার

আপনি যদি উইন্ডোতে থাকেন তবে ফাইলগুলি বাইনারি মোডে খুলতে ভুলবেন না
জন লা রুই

@gnibbler: বাইনারি মোডটি কেবলমাত্র অ-ডিফল্ট প্রোটোকলগুলির জন্য প্রয়োজন ( ডকস.পাইথন.আর.গ্রিবারি / পিকেল এইচটিএমএল#usage )।
এরিক হে লেবিগোট

উত্তর:


170

আপনার যদি একাধিক অবজেক্টগুলি সংরক্ষণ করতে হয়, আপনি কেবলমাত্র সেগুলি একটি একক তালিকায় রাখতে পারেন বা উদাহরণস্বরূপ:

import pickle

# obj0, obj1, obj2 are created here...

# Saving the objects:
with open('objs.pkl', 'w') as f:  # Python 3: open(..., 'wb')
    pickle.dump([obj0, obj1, obj2], f)

# Getting back the objects:
with open('objs.pkl') as f:  # Python 3: open(..., 'rb')
    obj0, obj1, obj2 = pickle.load(f)

আপনি ডাটা অনেক আছে, তাহলে আপনি পাশ দিয়ে ফাইল সাইজ কমে যায় protocol=-1থেকে dump(); pickleতারপরে ডিফল্ট historicalতিহাসিক (এবং আরও পিছিয়ে-সামঞ্জস্যপূর্ণ) প্রোটোকলের পরিবর্তে সেরা উপলব্ধ প্রোটোকল ব্যবহার করবে। এই ক্ষেত্রে ফাইলটি অবশ্যই বাইনারি মোডে ( wbএবং rbযথাক্রমে) খুলতে হবে ।

পাইথন 3 এর সাথে বাইনারি মোডটিও ব্যবহার করা উচিত, কারণ এর ডিফল্ট প্রোটোকলটি বাইনারি (অর্থাত্ অ-পাঠ্য) ডেটা (রাইটিং মোড 'wb'এবং রিডিং মোড 'rb') তৈরি করে।


12
পাইথন 3.5 তে, আমাকে "বাইট" মোডে ফাইলটি খুলতে হয়েছিল, যেমন with open('objs.pickle', 'wb') as f:(নোটটি নোট করুন wb)।
kbrose

হাই @ এরিক, খালি with open('objs.pkl') as f:তুলনা করার দরকার কী obj1, obj2 = pickle.load(open("objs.pkl","rb"))? এই দুজনের মধ্যে কি কোনও পার্থক্য আছে?
বালানডোঙ্গিভ

দ্বিতীয় ফর্মের সাহায্যে আপনি ফাইলটি বন্ধ করবেন না। এটি ভাল অনুশীলন হিসাবে বিবেচনা করা হয় না, কারণ সমান্তরালভাবে আপনি যে ফাইলগুলি খুলতে পারবেন তার সংখ্যা সাধারণত অপারেটিং সিস্টেমগুলি দ্বারা সীমাবদ্ধ থাকে (কোনও লুপ চেষ্টা করুন যা সেগুলি বন্ধ না করেই ফাইলগুলি খোল!)। এটি বলেছিল, বাস্তবে, ফাইলটি বন্ধ না করা প্রায়শই কাজ করে, যখন আপনি অনেকগুলি ফাইল খোলেন না।
এরিক হে লেবিগোট

49

সেখানে একটি অন্তর্নির্মিত গ্রন্থাগার রয়েছে picklepickleআপনি ব্যবহার করে কোনও ফাইলে অবজেক্ট ডাম্প করতে পারেন এবং সেগুলি পরে লোড করতে পারেন।

import pickle

f = open('store.pckl', 'wb')
pickle.dump(obj, f)
f.close()

f = open('store.pckl', 'rb')
obj = pickle.load(f)
f.close()

1
আই পাইথন ৩.৪ ব্যবহার করুন: f = open('store.pckl', 'wb')লিখতে ফাইল খুলতে। পড়ুন stackoverflow.com/questions/13906623/... এবং ব্যবহার `চ = খোলা ( 'store.pckl', 'RB') থেকে পড়া করার জন্য একটি ফাইল খুলুন। পড়ুন stackoverflow.com/questions/7031699/...
user3731622

এটি কি 3.4+ এর সাথে নির্দিষ্ট? আমি প্রায় উত্তরটি নিচে ভোট দিয়েছি কারণ যখন আপনি 'বি' ব্যবহার করবেন না তখন এটি ত্রুটি তৈরি করে।
উইলমার ই হেনাও

12

আপনার তাক এবং আচারের মডিউলগুলি দেখতে হবে। আপনার যদি প্রচুর ডেটা সঞ্চয় করতে হয় তবে ডাটাবেস ব্যবহার করা ভাল


আমি একটি একক বস্তু সংরক্ষণ করতে চাই যা একটি ক্লাউড সার্ভারে লগইন করে, হ্যান্ডেল করার জন্য যদি আমি সময়ের সাথে একাধিকবার লগইন করি তবে সার্ভারটি আমার অনুরোধটিকে প্রত্যাখ্যান করে। আচার মডিউলটি ব্যবহার করে কোনও ফাইলে কোনও বস্তুকে ফেলে দেওয়ার কোনও সুরক্ষা সমস্যা থাকতে পারে? উদাহরণস্বরূপ, যেখানে কোনও পাসওয়ার্ড ব্যবহার না করে আমার ক্লাউড-স্টোরেজে লগইন করতে পারে তার চেয়ে যদি কেউ আমার ডাম্পড বস্তুটি গ্রহণ করে।
আল্পার

5

একটি আচার ফাইলে একাধিক ভেরিয়েবল সংরক্ষণের জন্য অন্য পদ্ধতি:

import pickle

a = 3; b = [11,223,435];
pickle.dump([a,b], open("trial.p", "wb"))

c,d = pickle.load(open("trial.p","rb"))

print(c,d) ## To verify

4

আপনি ব্যবহার করতে পারেন klepto, যা মেমরি, ডিস্ক বা ডাটাবেসগুলিতে ক্রমাগত ক্যাশে সরবরাহ করে।

dude@hilbert>$ python
Python 2.7.6 (default, Nov 12 2013, 13:26:39) 
[GCC 4.2.1 Compatible Apple Clang 4.1 ((tags/Apple/clang-421.11.66))] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> from klepto.archives import file_archive
>>> db = file_archive('foo.txt')
>>> db['1'] = 1
>>> db['max'] = max
>>> squared = lambda x: x**2
>>> db['squared'] = squared
>>> def add(x,y):
...   return x+y
... 
>>> db['add'] = add
>>> class Foo(object):
...   y = 1
...   def bar(self, x):
...     return self.y + x
... 
>>> db['Foo'] = Foo
>>> f = Foo()
>>> db['f'] = f  
>>> db.dump()
>>> 

তারপরে, দোভাষী পুনরায় চালু করার পরে ...

dude@hilbert>$ python
Python 2.7.6 (default, Nov 12 2013, 13:26:39) 
[GCC 4.2.1 Compatible Apple Clang 4.1 ((tags/Apple/clang-421.11.66))] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> from klepto.archives import file_archive
>>> db = file_archive('foo.txt')
>>> db
file_archive('foo.txt', {}, cached=True)
>>> db.load()
>>> db
file_archive('foo.txt', {'1': 1, 'add': <function add at 0x10610a0c8>, 'f': <__main__.Foo object at 0x10510ced0>, 'max': <built-in function max>, 'Foo': <class '__main__.Foo'>, 'squared': <function <lambda> at 0x10610a1b8>}, cached=True)
>>> db['add'](2,3)
5
>>> db['squared'](3)
9
>>> db['f'].bar(4)
5
>>> 

কোডটি এখানে পান: https://github.com/uqfoundation


7
ওপি অন্তর্নির্মিত জন্য জিজ্ঞাসা করেনি।
মাইক ম্যাকার্নস

4

নিম্নলিখিত পদ্ধতিটি সহজ বলে মনে হচ্ছে এবং বিভিন্ন আকারের ভেরিয়েবলের সাথে ব্যবহার করা যেতে পারে:

import hickle as hkl
# write variables to filename [a,b,c can be of any size]
hkl.dump([a,b,c], filename)

# load variables from filename
a,b,c = hkl.load(filename)

hickleপ্যাকেজটি আরও শক্ত (কম ত্রুটির প্রবণ) এবং এর চেয়েও সহজ (কম কোড) pickle
ব্যবহারকারী 2340939
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.