Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Pickle - Load variable if exists or create and save it

Tags:

Is there a better way to load a variable with pickle if it already exists or create it and dump it if it doesn't?

if os.path.isfile("var.pickle"):     foo = pickle.load( open( "var.pickle", "rb" ) ) else:     foo = 3     pickle.dump( foo, open( "var.pickle", "wb" ) ) 
like image 815
Matteo Avatar asked Nov 10 '14 01:11

Matteo


People also ask

How do you load data with pickles?

Python Pickle load You have to use pickle. load() function to do that. The primary argument of pickle load function is the file object that you get by opening the file in read-binary (rb) mode. Simple!

What does pickle load () return?

This class takes a binary file for reading a pickle data stream. load() – This function is used to read a pickled object representation from the open file object file and return the reconstituted object hierarchy specified.


2 Answers

You can follow the EAFP principle and ask for forgiveness:

import pickle  try:     foo = pickle.load(open("var.pickle", "rb")) except (OSError, IOError) as e:     foo = 3     pickle.dump(foo, open("var.pickle", "wb")) 
like image 185
alecxe Avatar answered Sep 22 '22 03:09

alecxe


I'd put it in a function for reusability, avoid error catching for control flow on the file, as it's less efficient, and I would use context managers to open the file.

import os import pickle  def read_or_new_pickle(path, default):     if os.path.isfile(path):         with open(path, "rb") as f:             try:                 return pickle.load(f)             except Exception: # so many things could go wrong, can't be more specific.                 pass      with open(path, "wb") as f:         pickle.dump(default, f)     return default 

usage:

foo = read_or_new_pickle(path="var.pickle", default=3) 

foo returns 3

foo = read_or_new_pickle(path="var.pickle", default=4) 

and foo still returns 3.

Admittedly, the following is rather short and elegant, but too many things could go wrong, and you'd have to catch everything (don't believe me? try this: import io, pickle; pickle.load(io.BytesIO(b"\x00")) and play with the binary):

import pickle  def read_or_new_pickle(path, default):     try:         foo = pickle.load(open(path, "rb"))     except Exception:         foo = default         pickle.dump(foo, open(path, "wb"))     return foo 

Same usage. But I'm concerned the file might not be closed fast enough to avoid an error on opening it the second time in the event of a empty or malformed file. So use the context manager:

import pickle  def read_or_new_pickle(path, default):     try:         with open(path, "rb") as f:             foo = pickle.load(f)     except Exception:         foo = default         with open(path, "wb") as f:             pickle.dump(foo, f)     return foo 
like image 44
Russia Must Remove Putin Avatar answered Sep 26 '22 03:09

Russia Must Remove Putin