0

everyone.

I was tinkering with ways to store dictionaries and retrieve them later, loading them into and replacing the existing dictionary values.

I was intending to use this as a way to store game data in a simple text-based game.

# Player dictionaries

p1 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}
p2 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}
p3 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}
p4 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}
p5 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}
p6 = {'name' : "placeholder", 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0,
      'atk': 0, 'def': 0, 'cyra' : 0, 'monero' : 0, 'bits': 0, 'dollars': 0,
      'nordas': 0,}

#save function
import pickle
def save() :
    f = open("p1.txt","w")
    f.write( str(p1) )
    f.close()

    f = open("p2.txt","w")
    f.write( str(p2) )
    f.close()

    f = open("p3.txt","w")
    f.write( str(p3) )
    f.close()

    f = open("p4.txt","w")
    f.write( str(p4) )
    f.close()

    f = open("p5.txt","w")
    f.write( str(p5) )
    f.close()

    f = open("p6.txt","w")
    f.write( str(p6) )
    f.close()

    print ("The game was saved.")

To my delight, I discovered that this does work, and it creates six files names "p1.txt", "p2.txt", and so forth in the folder that the program is saved. It looks exactly like the original dictionary:

{'name': 'placeholder', 'hp': 0, 'str': 0, 'stm': 0, 'mana': 0, 'atk': 0, 'def': 0, 'cyra': 0, 'monero': 0, 'bits': 0, 'dollars': 0, 'nordas': 0}

However, upon attempting to try and create an import_save() function, I ran into a problem. I couldn't use unpickle(), because that's not how I exported the dictionary in the first place. Any tips on how this could be solved?

I was also looking to find a way that the imported dictionary could over-write the existing dictionary? I couldn't find anything about it... I'm not against re-writing the code if that is needed.

  • 1
    Just a thought, but why not use the [`json` module](https://docs.python.org/3/library/json.html) instead. Also it's better IMO too wrap open in a `with` context. – Mark Mikofski Jan 07 '18 at 03:30
  • might help if you show us your `import_save()` function – ShpielMeister Jan 07 '18 at 03:37
  • 1
    also why 6 file? just add all the dict in the list or another dict and store it in a single file using `json.dump` (and read it again using `json.load`) – Moinuddin Quadri Jan 07 '18 at 03:41
  • Patrick Haugh I agree, [this answer](https://stackoverflow.com/a/11027016/1020470) has the `pickle` alternative to using `json` and avoids the dangerous evil function that shall not be named – Mark Mikofski Jan 07 '18 at 03:46
  • 1
    I'm not a fan of `json` for this because not all python dictionaries conform to the [`json` standard](https://json.org/). I would probably use either `ast.literal_eval` or `pickle` – Patrick Haugh Jan 07 '18 at 03:51

2 Answers2

3

Try this instead:

import json

# save to file
with open("p1.txt", "w") as f:
    json.dump(p1, f)

# read from file
with open("p1.txt", "r") as f:
    p1 = json.load(f)

Although as Patrick Haugh mentions, and the duplicate answer also indicates, json will convert all dictionary keys to unicode strings, so, for example, if you had integers like {1: 'a'} decoded would be {u'1': u'a'} which is not the same as the original dictionary - note the key is now a string, not an integer. Using the pickle module would avoid this particular issue, but it is not human readable, nor is it readable by other computer languages - pickle is a Python object serialization.

Mark Mikofski
  • 19,398
  • 2
  • 57
  • 90
1

As @Mark suggested, json is the best way:

import json

p_list = [p1, p2, p3, p4, p5, p6]

# Write
for i in range(1, 7):
    with open('p'+str(i)+'.json', 'w') as f:
        json.dump(p_list[i-1], f)

#Read
p_read_list = list()
for i in range(1, 7):
    with open('p'+str(i)+'.json', 'r') as f:
        p_read_list.append(json.load(f))

print(p_read_list[0])
Ganesh Kathiresan
  • 2,068
  • 2
  • 22
  • 33