简体   繁体   中英

How to replace strings in a list using tuples of strings and their replacements?

I have a list of player ranks attributed to players. In addition to this, I have a list of tuples of ranks...

rank_database = [("Unprocessed Rank", "Processed Rank"), ("Unprocessed Rank 2", "Processed Rank 2")]

What I would like to do is, for every item in the player ranks list, process them through the rank database --- like find and replace.

So, before replacement:

player_ranks = ["Unprocessed Rank", "Unprocessed Rank 2"]

After replacement:

player_ranks = ["Processed Rank", "Processed Rank 2"]

Essentially, I would like to use rank_database to perform a find and replace operation on the player_ranks list.

Proposed Solution

My idea was to try to use the tuples with the str.replace method as follows...

player_ranks = ["Unprocessed Rank", "Unprocessed Rank 2"]
rank_database = [("Unprocessed Rank", "Processed Rank"), ("Unprocessed Rank 2", "Processed Rank 2")]

for x in player_ranks:
    for y in rank_database:
        print("Changed "+x+" to")
        if x == y[0]:
            player_ranks[x].replace(rank_database[y]) #Line 5
            print (x)
            break
        else:
            continue
print("Finished!")

When I execute the code, since ("Unprocessed Rank", "Processed Rank") is a tuple found at rank_database[i] , I'm hoping this will sort of "inject" the tuple as the replacement strings in the str.replace method.

So, when executing the code, Line 5 should look like...

rank.replace(("Unprocessed Rank", "Processed Rank"))

Would this be a possible solution, or is this not possible, and would other solutions be more appropriate? This is for a personal project, so I would prefer to get my own solution working.

I'm making these assumptions:

  1. The "unprocessed" ranks in your database are unique, because otherwise you'll have to add a way to determine which tuple is the "correct" mapping from that unprocessed rank to a processed one.

  2. Returning a new list of processed ranks is as good as mutating the original list.

  3. Your data will all fit in memory easily, because this will take at least twice the memory your database already uses.

Your database should be stored as a dict , or at least should be converted into one for the kind of work you're doing, since all you're doing is mapping unique(?) keys to values. The dict initializer can take an iterable of key-value pairs, which you already have.

Below, I've created a stand-alone function to do the work.

#!/usr/bin/env python3

def process_ranks(player_ranks, rank_database):
    rank_map = dict(rank_database)
    return [rank_map[rank] for rank in player_ranks]

def main():
    # Sample data.
    player_ranks = ['old' + str(n) for n in range(4)]
    # Database contains more rank data than we will use.
    rank_database = [
      ('old' + str(n), 'new' + str(n)) for n in range(40)
      ]

    print("Original player ranks:")
    print(player_ranks)
    processed_ranks = process_ranks(player_ranks, rank_database)
    print("Processed player ranks:")
    print(processed_ranks)
    return

if "__main__" == __name__:
    main()

Output:

Original player ranks:
['old0', 'old1', 'old2', 'old3']
Processed player ranks:
['new0', 'new1', 'new2', 'new3']

If you really do need to mutate the original list, you could replace its contents with a slightly different call to process_ranks in main with:

    player_ranks[:] = process_ranks(player_ranks, rank_database)

In general, though, I find preserving the original list and creating a new processed_ranks list is easier to code and especially to debug.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM