When the gacha service is actually operated, it is necessary to add new items on a regular basis.
In the data structure up to Last time, it was necessary to rewrite the Gacha item information
when it was time to add an item.
Therefore, let's consider a data structure that meets the following function requests.
――I want to set the implementation period of gacha --I want to automatically add lottery items when the gacha period changes.
gacha
id | start_time | end_time | gacha_group | gacha_lottery_id |
---|---|---|---|---|
1 | 2020-05-01 00:00:00 | 2020-05-31 23:59:59 | A | normal_1 |
2 | 2020-05-01 00:00:00 | 2020-05-31 23:59:59 | A | normal_11 |
3 | 2020-05-25 00:00:00 | 2020-05-31 23:59:59 | B | fighter_2 |
4 | 2020-06-01 00:00:00 | 2020-06-04 23:59:59 | C | omake_2_11 |
5 | 2020-05-20 00:00:00 | 2020-05-31 23:59:59 | A | omake_fighter_6 |
6 | 2020-06-01 00:00:00 | 2020-06-30 23:59:59 | C | normal_1 |
7 | 2020-06-01 00:00:00 | 2020-06-30 23:59:59 | C | normal_11 |
The blue (1 and 2) </ font> and red (6 and 7) </ font> IDs use the same gacha_lottery_id, respectively. , The lottery group target to be used differs as follows.
--Groups subject to lottery until May 31, 2020: ʻA --Groups subject to lottery from June 1, 2020:
C`
If you set each period in this way, you can switch without updating the gacha item information at that time. The settings are summarized below.
--Start and end of gacha implementation period (start_time, end_time) --Lottery target group (gacha_group) within the period --Corresponding gacha method definition ID (gacha_lottery_id)
gacha_lottery
id | item_type | times | rarity | omake_times | omake_rarity | cost |
---|---|---|---|---|---|---|
normal_1 | 0 | 1 | 0 | 0 | 0 | 10 |
normal_11 | 0 | 10 | 0 | 1 | 3 | 100 |
fighter_2 | 0 | 2 | 0 | 0 | 0 | 30 |
omake_2_11 | 0 | 9 | 2 | 2 | 3 | 150 |
omake_fighter_6 | 2 | 5 | 0 | 1 | 3 | 100 |
The management of the lottery target group (gacha_group) will be transferred to Gacha information
, and the information will be linked to each other by gacha_lottery_id.
The group prefix (A or B) has been removed from the ID because it no longer has a lottery control group (gacha_group) item
gacha.py
import random
from datetime import datetime
def gacha(lots, times: int=1) -> list:
return random.choices(tuple(lots), weights=lots.values(), k=times)
def get_rarity_name(rarity: int) -> str:
rarity_names = {5: "UR", 4: "SSR", 3: "SR", 2: "R", 1: "N"}
return rarity_names[rarity]
#Gacha information dictionary
def get_gacha_info(now_time: int) -> dict:
gachas = {
1: {"start_time": "2020-05-01 00:00:00", "end_time": "2020-05-31 23:59:59", "gacha_group": "A",
"gacha_lottery_id": "normal_1"},
2: {"start_time": "2020-05-01 00:00:00", "end_time": "2020-05-31 23:59:59", "gacha_group": "A",
"gacha_lottery_id": "normal_11"},
3: {"start_time": "2020-05-25 00:00:00", "end_time": "2020-05-31 23:59:59", "gacha_group": "B",
"gacha_lottery_id": "fighter_2"},
4: {"start_time": "2020-06-01 00:00:00", "end_time": "2020-06-04 23:59:59", "gacha_group": "C",
"gacha_lottery_id": "omake_2_11"},
5: {"start_time": "2020-05-20 00:00:00", "end_time": "2020-05-31 23:59:59", "gacha_group": "A",
"gacha_lottery_id": "omake_fighter_6"},
6: {"start_time": "2020-06-01 00:00:00", "end_time": "2020-06-30 23:59:59", "gacha_group": "C",
"gacha_lottery_id": "normal_1"},
7: {"start_time": "2020-06-01 00:00:00", "end_time": "2020-06-30 23:59:59", "gacha_group": "C",
"gacha_lottery_id": "normal_11"}
}
results = {}
for gacha_id, info in gachas.items():
start_time = int(datetime.strptime(info["start_time"], '%Y-%m-%d %H:%M:%S').timestamp())
end_time = int(datetime.strptime(info["end_time"], '%Y-%m-%d %H:%M:%S').timestamp())
#Narrow down the target gacha information within the range of the date and time
if start_time <= now_time <= end_time:
results[gacha_id] = info
return results
#Dictionary of gacha method definition information
def get_gacha_lottery_info(gacha_lottery_id: str) -> dict:
# gacha_Transferred group
gacha_lottery = {
"normal_1": {"item_type": 0, "times": 1, "rarity": 0, "omake_times": 0, "omake_rarity": 0, "cost":10},
"normal_11": {"item_type": 0, "times": 10, "rarity": 0, "omake_times": 1, "omake_rarity": 3, "cost":100},
"fighter_2": {"item_type": 0, "times": 2, "rarity": 0, "omake_times": 0, "omake_rarity": 0, "cost":30},
"omake_2_11": {"item_type": 0, "times": 9, "rarity": 2, "omake_times": 2, "omake_rarity": 3, "cost":150},
"omake_fighter_6": {"item_type": 2, "times": 5, "rarity": 0, "omake_times": 1, "omake_rarity": 3, "cost":100}
}
return gacha_lottery[gacha_lottery_id]
def set_gacha(items: dict, gacha_items: dict):
#Include the item information required for gacha settings in the gacha item information
dic_gacha_items = {}
for gacha_item_id, info in gacha_items.items():
info["item_info"] = items[info["item_id"]]
dic_gacha_items[gacha_item_id] = info
#Extract the lottery target list
def get_lots(lottery_info: dict):
lots = {}
omake_lots = {}
for id, info in dic_gacha_items.items():
if lottery_info["gacha_group"] != info["gacha_group"]:
continue
if lottery_info["item_type"] and lottery_info["item_type"] != info["item_info"]["item_type"]:
continue
if not(lottery_info["rarity"]) or lottery_info["rarity"] <= info["item_info"]["rarity"]:
lots[id] = info["weight"]
if lottery_info["omake_times"]:
if not(lottery_info["omake_rarity"]) or lottery_info["omake_rarity"] <= info["item_info"]["rarity"]:
omake_lots[id] = info["weight"]
return lots, omake_lots
#Gacha execution
def exec(gacha_lottery_id: str, now_time: int=0) -> list:
if not now_time: now_time = int(datetime.now().timestamp())
#Get executable gacha information
gachas = get_gacha_info(now_time)
lottery_info = get_gacha_lottery_info(gacha_lottery_id)
ids = []
for gacha_id, gacha_info in gachas.items():
if gacha_lottery_id == gacha_info["gacha_lottery_id"]:
lottery_info["gacha_group"] = gacha_info["gacha_group"]
print("==%s==:gacha_group:%s" % (gacha_lottery_id, lottery_info["gacha_group"]))
lots, omake_lots =get_lots(lottery_info)
ids = gacha(lots, lottery_info["times"])
if len(omake_lots) > 0:
ids.extend(gacha(omake_lots, lottery_info["omake_times"]))
return ids
return exec
def main():
#Item information
items = {
5101: {"rarity": 5, "item_name": "UR_Brave", "item_type": 1, "hp": 1200},
4201: {"rarity": 4, "item_name": "SSR_Warrior", "item_type": 2, "hp": 1000},
4301: {"rarity": 4, "item_name": "SSR_Wizard", "item_type": 3, "hp": 800},
4401: {"rarity": 4, "item_name": "SSR_Priest", "item_type": 4, "hp": 800},
3201: {"rarity": 3, "item_name": "SR_Warrior", "item_type": 2, "hp": 600},
3301: {"rarity": 3, "item_name": "SR_Wizard", "item_type": 3, "hp": 500},
3401: {"rarity": 3, "item_name": "SR_Priest", "item_type": 4, "hp": 500},
2201: {"rarity": 2, "item_name": "R_Warrior", "item_type": 2, "hp": 400},
2301: {"rarity": 2, "item_name": "R_Wizard", "item_type": 3, "hp": 300},
2401: {"rarity": 2, "item_name": "R_Priest", "item_type": 4, "hp": 300},
3199: {"rarity": 3, "item_name": "SR_Brave", "item_type": 1, "hp": 600},
#Added below
4101: {"rarity": 4, "item_name": "SSR_Brave", "item_type": 1, "hp": 1000},
5201: {"rarity": 5, "item_name": "UR_Warrior", "item_type": 2, "hp": 1300},
5301: {"rarity": 5, "item_name": "UR_Wizard", "item_type": 3, "hp": 1000},
}
#Gacha item information
gacha_items = {
1: {"gacha_group": "A", "weight": 3, "item_id": 5101},
2: {"gacha_group": "A", "weight": 9, "item_id": 4201},
3: {"gacha_group": "A", "weight": 9, "item_id": 4301},
4: {"gacha_group": "A", "weight": 9, "item_id": 4401},
5: {"gacha_group": "A", "weight": 20, "item_id": 3201},
6: {"gacha_group": "A", "weight": 20, "item_id": 3301},
7: {"gacha_group": "A", "weight": 20, "item_id": 3401},
8: {"gacha_group": "A", "weight": 40, "item_id": 2201},
9: {"gacha_group": "A", "weight": 40, "item_id": 2301},
10: {"gacha_group": "A", "weight": 40, "item_id": 2401},
11: {"gacha_group": "B", "weight": 15, "item_id": 4201},
12: {"gacha_group": "B", "weight": 30, "item_id": 3201},
13: {"gacha_group": "B", "weight": 55, "item_id": 2201},
#Added below
14: {"gacha_group": "C", "weight": 1, "item_id": 5101},
15: {"gacha_group": "C", "weight": 1, "item_id": 5201},
16: {"gacha_group": "C", "weight": 1, "item_id": 5301},
17: {"gacha_group": "C", "weight": 9, "item_id": 4101},
18: {"gacha_group": "C", "weight": 6, "item_id": 4201},
19: {"gacha_group": "C", "weight": 6, "item_id": 4301},
20: {"gacha_group": "C", "weight": 6, "item_id": 4401},
21: {"gacha_group": "C", "weight": 20, "item_id": 3201},
22: {"gacha_group": "C", "weight": 20, "item_id": 3301},
23: {"gacha_group": "C", "weight": 20, "item_id": 3401},
24: {"gacha_group": "C", "weight": 40, "item_id": 2201},
25: {"gacha_group": "C", "weight": 40, "item_id": 2301},
26: {"gacha_group": "C", "weight": 40, "item_id": 2401},
}
#Gacha tuple to carry out
gacha_lottery_ids = (
"normal_1","normal_11","fighter_2","omake_2_11","omake_fighter_6"
)
#Specify the gacha execution date and time to check the operation
now_time = int(datetime.strptime("2020-06-01 00:00:00", '%Y-%m-%d %H:%M:%S').timestamp())
#Set items etc.
func_gacha = set_gacha(items, gacha_items)
# gacha_lottery_Execute gacha with id setting
for gacha_lottery_id in gacha_lottery_ids:
ids = func_gacha(gacha_lottery_id,now_time)
for id in ids:
item_info = items[gacha_items[id]["item_id"]]
print("ID:%d, %s, %s" % (id, get_rarity_name(item_info["rarity"]), item_info["item_name"]))
if __name__ == '__main__':
main()
The program is written so that the gacha is executed by specifying gacha_lottery_id
so that it is easy to understand that the target gacha group is switched depending on the execution date and time.
==normal_1==:gacha_group:C
ID:26, R, R_Priest
==normal_11==:gacha_group:C
ID:25, R, R_Wizard
ID:22, SR, SR_Wizard
ID:26, R, R_Priest
ID:24, R, R_Warrior
ID:25, R, R_Wizard
ID:21, SR, SR_Warrior
ID:15, UR, UR_Warrior
ID:24, R, R_Warrior
ID:23, SR, SR_Priest
ID:24, R, R_Warrior
ID:21, SR, SR_Warrior
==omake_2_11==:gacha_group:C
ID:21, SR, SR_Warrior
ID:25, R, R_Wizard
ID:24, R, R_Warrior
ID:21, SR, SR_Warrior
ID:23, SR, SR_Priest
ID:25, R, R_Wizard
ID:23, SR, SR_Priest
ID:18, SSR, SSR_Warrior
ID:25, R, R_Wizard
ID:23, SR, SR_Priest
ID:17, SSR, SSR_Brave
In the actual game, as shown in the flow below, the gacha will be executed by specifying gacha_id
, so the program configuration will be slightly different.
Recommended Posts