Hash(Dictionary) stored in a List

I am teaching High School programming in Python and wanted to do a class activity where we make a Pokemon style battle system. (I have one from last year I did in Ruby which works fine). The idea is a random number is generated in a variable and this is used to determine which wild Pokemon attacks the player. I have a list called "wild_pokemon" and I want to store a Hash with key information for each potential wild pokemon the player can battle. So Pikachu and his data would be a Hash stored in index 0, the mr_mime hash in index 1 etc. I like the nested Hash as you can give the data clear names such as "name" or "type".

I am writing a basic test of this in Python and get a error with the nesting of the Hash and can't find any info as to why. The = in the Pikachu Hash is highlighted and it says invalid syntax.

I hope this is clear.

import random
import time

wild_pokemon=[pikachu={"Name":"Pikachu", "Type":"Eletric", "Level":random.randint(1,3), "Health":random.randint(15,25),},#List with nested hashes
              mr_mime={"Name":"Mr Mime", "Type":"Lame", "Level":random.randint(1,3), "Health":random.randint(5,10), },
              weedle={"Name":"Weddle", "Type"=>"Bug", "Level":random.randint(1,3), "Health":rand(4,12), }]

def battle():# Placeholdr until i can fix error with the List.
    print("test")


battle()

Answers 1

  • In python list you don't need to assign the values to keyword. Just store the dicts.

    import random
    import time
    
    wild_pokemon=[{"Name":"Pikachu", "Type":"Eletric", "Level":random.randint(1,3), "Health":random.randint(15,25)},#List with nested hashes
                  {"Name":"Mr Mime", "Type":"Lame", "Level":random.randint(1,3), "Health":random.randint(5,10)},
                  {"Name":"Weddle", "Type":"Bug", "Level":random.randint(1,3), "Health":random.randint(4,12)}]
    
    def battle():
        pos = random.randint(0, 2)
        pokemon = wild_pokemon[pos]
        return pos, pokemon
    
    
    print(battle())
    

    Output:

    (1, {'Name': 'Mr Mime', 'Type': 'Lame', 'Level': 2, 'Health': 8})
    

    You could also go with random.choice and use a nested dict instead of a list:

    import random
    import time
    
    wild_pokemon=dict(pikachu={"Name":"Pikachu", "Type":"Eletric", "Level":random.randint(1,3), "Health":random.randint(15,25)},#List with nested hashes
                  mr_mime={"Name":"Mr Mime", "Type":"Lame", "Level":random.randint(1,3), "Health":random.randint(5,10)},
                  weedle={"Name":"Weddle", "Type":"Bug", "Level":random.randint(1,3), "Health":random.randint(4,12)})
    
    def battle():# Placeholdr until i can fix error with the List.
        name = random.choice(list(wild_pokemon.keys()))
        pokemon = wild_pokemon[name]
        return name, pokemon
    
    print(battle())
    

    Output:

    ('pikachu', {'Name': 'Pikachu', 'Type': 'Eletric', 'Level': 2, 'Health': 23})
    

    You could also use collections.namedtuple instead of a list, if you want both index and names:

    import random
    import time
    from collections import namedtuple
    pokemon = namedtuple('pokemon', 'pikachu mr_mime weedle')
    wild_pokemon=pokemon(pikachu={"Name":"Pikachu", "Type":"Eletric", "Level":random.randint(1,3), "Health":random.randint(15,25)},#List with nested hashes
                  mr_mime={"Name":"Mr Mime", "Type":"Lame", "Level":random.randint(1,3), "Health":random.randint(5,10)},
                  weedle={"Name":"Weddle", "Type":"Bug", "Level":random.randint(1,3), "Health":random.randint(4,12)})
    
    def battle():# Placeholdr until i can fix error with the List.
        pos = random.randint(0, 2)
        pokemon = wild_pokemon[pos]
        return pos, pokemon
    
    print(wild_pokemon.pikachu)
    print(battle())
    

    Output:

    {'Name': 'Pikachu', 'Type': 'Eletric', 'Level': 1, 'Health': 24}
    (0, {'Name': 'Pikachu', 'Type': 'Eletric', 'Level': 1, 'Health': 24})
    

Related Articles