0

I'm trying to eventually create a matrix style raining code animation with Pygame.

I'm stuck in the beginning, where I wanted to assign coordinates for each character, because:

I can't have duplicate keys in a dict, so this structure won't work:

CharacterMatrix = {character : [xPos, yPos]} 

but I also can't have the unique coordinate as a Key, because dict's wont accept lists as keys, so of course this also won't work:

CharacterMatrix = {[xPos, yPos] : character } 

My question now is: How would you elegantly store a large amount of non-unique random chars with corresponding x and y coordinates?

Thanks a lot and sorry, if I oversaw a similar question!

Thilo G
  • 95
  • 5

2 Answers2

1

In python dicts accept immutable types as keys, so use tuple instead of list.

EDIT Example:

In [1]: d = {(1, 2,): 'a', (1, 1): 'b', (2, 1): 'c', (2, 2): 'd'}

In [2]: d[(1, 1)]
Out[2]: 'b'
gonczor
  • 3,994
  • 1
  • 21
  • 46
0

You do not store a matrix, you store columns as "sentences", using zip you create rows from them:

c = ["SHOW", "ME  ", "THIS"]
r = [' '.join(row) for row in zip(*c)]
print (c)
for n in r:
    print(n)

Output:

['SHOW', 'ME  ', 'THIS']
S M T
H E H
O   I
W   S

Now you just need to mutate the content - you can slice the strings:

c[1] = "!"+c[1][:-1]
r = [' '.join(row) for row in zip(*c)]
for n in r:
    print(n)

Output:

S ! T
H M H
O E I
W   S

A matrix would be cumbersome, you want to scroll single columns down while others stand still and might want to replace single characters. Using a matrix would need you to downshift a lot all the time, far easier to modify a "column-sentence" (as above) or a list of strings:

from string import ascii_letters, digits
from itertools import product
import random
import os
import time

random.seed(42) # remove for more randomness
numCols = 10
numRows = 20
allCoods = list(product(range(numCols),range(numRows))) # for single char replacement

pri = ascii_letters + digits + '`?=)(/&%$§"!´~#'        # thats what we display

# cred:  https://stackoverflow.com/a/684344/7505395
def cls():                         
    os.system('cls' if os.name=='nt' else 'clear') 


def modCol(columns, which):
  for (c,r) in which:
    # replace change random characters
    newOne = random.choice(pri)
    columns[c] =  columns[c][:r]+[newOne]+columns[c][r+1:]

  for i in range(len(columns)):
    if (random.randint(0,5) > 2):
      # scroll some lines down by 1
      columns[i].insert(0,random.choice(pri))
      columns[i] = columns[i][:-1]

# creates random data for columns
cols = [random.choices(pri ,k=numRows ) for _ in range(numCols)]

while True:
  cls()
  # zip changes your columns-list into a row-tuple, the joins for printing
  print ( '\n'.join(' '.join(row) for row in zip(*cols)))
  time.sleep(1)
  # which characters to change?
  choi =  random.choices(allCoods, k=random.randint(0,(numCols*numRows)//3))
  modCol(cols, choi )
Patrick Artner
  • 50,409
  • 9
  • 43
  • 69