drop proactive + analysis

This commit is contained in:
2023-08-18 22:35:48 -04:00
parent 70a2d7da51
commit f3f50accaa
34 changed files with 20785 additions and 8284 deletions

214
model.py
View File

@@ -23,7 +23,7 @@ class Model(ap.Model):
# external variable
self.int_n_max_trial = int(self.p.n_max_trial)
self.is_prf_size = bool(self.p.prf_size)
self.proactive_ratio = float(self.p.proactive_ratio)
# self.proactive_ratio = float(self.p.proactive_ratio) # dropped
self.remove_t = int(self.p.remove_t)
self.int_netw_prf_n = int(self.p.netw_prf_n)
@@ -231,114 +231,114 @@ class Model(ap.Model):
product]['p_stat'].append(('D', self.t))
# print(f"initial disruption {firm.name} {product.code}")
# proactive strategy
# get all the firm prod affected
for firm, a_lst_product in self.dct_lst_init_disrupt_firm_prod.items():
for product in a_lst_product:
init_node = \
[n for n, v in
self.firm_prod_network.nodes(data=True)
if v['Firm_Code'] == firm.code and
v['Product_Code'] == product.code][0]
dct_affected = \
nx.dfs_successors(self.firm_prod_network,
init_node)
lst_affected = set()
for i, (u, vs) in enumerate(dct_affected.items()):
# at least 2 hops away
if i > 0:
pred_node = self.firm_prod_network.nodes[u]
for v in vs:
succ_node = self.firm_prod_network.nodes[v]
lst_affected.add((succ_node['Firm_Code'],
succ_node['Product_Code']))
lst_affected = list(lst_affected)
lst_firm_proactive = \
[lst_affected[i] for i in
self.nprandom.choice(range(len(lst_affected)),
round(len(lst_affected) *
self.proactive_ratio),
replace=False)]
# # proactive strategy (dropped)
# # get all the firm prod affected
# for firm, a_lst_product in self.dct_lst_init_disrupt_firm_prod.items():
# for product in a_lst_product:
# init_node = \
# [n for n, v in
# self.firm_prod_network.nodes(data=True)
# if v['Firm_Code'] == firm.code and
# v['Product_Code'] == product.code][0]
# dct_affected = \
# nx.dfs_successors(self.firm_prod_network,
# init_node)
# lst_affected = set()
# for i, (u, vs) in enumerate(dct_affected.items()):
# # at least 2 hops away
# if i > 0:
# pred_node = self.firm_prod_network.nodes[u]
# for v in vs:
# succ_node = self.firm_prod_network.nodes[v]
# lst_affected.add((succ_node['Firm_Code'],
# succ_node['Product_Code']))
# lst_affected = list(lst_affected)
# lst_firm_proactive = \
# [lst_affected[i] for i in
# self.nprandom.choice(range(len(lst_affected)),
# round(len(lst_affected) *
# self.proactive_ratio),
# replace=False)]
for firm_code, prod_code in lst_firm_proactive:
pro_firm_prod_code = \
[n for n, v in
self.firm_prod_network.nodes(data=True)
if v['Firm_Code'] == firm_code and
v['Product_Code'] == prod_code][0]
pro_firm_prod_node = \
self.firm_prod_network.nodes[pro_firm_prod_code]
pro_firm = \
self.a_lst_total_firms.select(
[firm.code == pro_firm_prod_node['Firm_Code']
for firm in self.a_lst_total_firms])[0]
lst_shortest_path = \
list(nx.all_shortest_paths(self.firm_prod_network,
source=init_node,
target=pro_firm_prod_code))
# for firm_code, prod_code in lst_firm_proactive:
# pro_firm_prod_code = \
# [n for n, v in
# self.firm_prod_network.nodes(data=True)
# if v['Firm_Code'] == firm_code and
# v['Product_Code'] == prod_code][0]
# pro_firm_prod_node = \
# self.firm_prod_network.nodes[pro_firm_prod_code]
# pro_firm = \
# self.a_lst_total_firms.select(
# [firm.code == pro_firm_prod_node['Firm_Code']
# for firm in self.a_lst_total_firms])[0]
# lst_shortest_path = \
# list(nx.all_shortest_paths(self.firm_prod_network,
# source=init_node,
# target=pro_firm_prod_code))
dct_drs = {}
for di_supp_code in self.firm_prod_network.predecessors(
pro_firm_prod_code):
di_supp_node = \
self.firm_prod_network.nodes[di_supp_code]
di_supp_prod = \
self.a_lst_total_products.select(
[product.code == di_supp_node['Product_Code']
for product in self.a_lst_total_products])[0]
di_supp_firm = \
self.a_lst_total_firms.select(
[firm.code == di_supp_node['Firm_Code']
for firm in self.a_lst_total_firms])[0]
lst_cand = self.a_lst_total_firms.select([
firm.is_prod_in_current_normal(di_supp_prod)
for firm in self.a_lst_total_firms
])
n2n_betweenness = \
sum([True if di_supp_code in path else False
for path in lst_shortest_path]) \
/ len(lst_shortest_path)
drs = n2n_betweenness / \
(len(lst_cand) * di_supp_firm.size_stat[-1][0])
dct_drs[di_supp_code] = drs
dct_drs = dict(sorted(
dct_drs.items(), key=lambda kv: kv[1], reverse=True))
for di_supp_code in dct_drs.keys():
di_supp_node = \
self.firm_prod_network.nodes[di_supp_code]
di_supp_prod = \
self.a_lst_total_products.select(
[product.code == di_supp_node['Product_Code']
for product in self.a_lst_total_products])[0]
# find a dfferent firm can produce the same product
# and is not a current supplier for the same product
lst_current_supp_code = \
[self.firm_prod_network.nodes[code]['Firm_Code']
for code in self.firm_prod_network.predecessors(
pro_firm_prod_code)
if self.firm_prod_network.nodes[code][
'Product_Code'] == di_supp_prod.code]
lst_cand = self.model.a_lst_total_firms.select([
firm.is_prod_in_current_normal(di_supp_prod)
and firm.code not in lst_current_supp_code
for firm in self.model.a_lst_total_firms
])
if len(lst_cand) > 0:
select_cand = self.nprandom.choice(lst_cand)
self.firm_network.graph.add_edges_from([
(self.firm_network.positions[select_cand],
self.firm_network.positions[pro_firm], {
'Product': di_supp_prod.code
})
])
# print(f"proactive add {select_cand.name} to "
# f"{pro_firm.name} "
# f"for {di_supp_node['Firm_Code']} "
# f"{di_supp_node['Product_Code']}")
# change capacity
select_cand.dct_prod_capacity[di_supp_prod] -= 1
break
# nx.to_pandas_adjacency(G_Firm).to_csv('adj_g_firm_proactive.csv')
# dct_drs = {}
# for di_supp_code in self.firm_prod_network.predecessors(
# pro_firm_prod_code):
# di_supp_node = \
# self.firm_prod_network.nodes[di_supp_code]
# di_supp_prod = \
# self.a_lst_total_products.select(
# [product.code == di_supp_node['Product_Code']
# for product in self.a_lst_total_products])[0]
# di_supp_firm = \
# self.a_lst_total_firms.select(
# [firm.code == di_supp_node['Firm_Code']
# for firm in self.a_lst_total_firms])[0]
# lst_cand = self.a_lst_total_firms.select([
# firm.is_prod_in_current_normal(di_supp_prod)
# for firm in self.a_lst_total_firms
# ])
# n2n_betweenness = \
# sum([True if di_supp_code in path else False
# for path in lst_shortest_path]) \
# / len(lst_shortest_path)
# drs = n2n_betweenness / \
# (len(lst_cand) * di_supp_firm.size_stat[-1][0])
# dct_drs[di_supp_code] = drs
# dct_drs = dict(sorted(
# dct_drs.items(), key=lambda kv: kv[1], reverse=True))
# for di_supp_code in dct_drs.keys():
# di_supp_node = \
# self.firm_prod_network.nodes[di_supp_code]
# di_supp_prod = \
# self.a_lst_total_products.select(
# [product.code == di_supp_node['Product_Code']
# for product in self.a_lst_total_products])[0]
# # find a dfferent firm can produce the same product
# # and is not a current supplier for the same product
# lst_current_supp_code = \
# [self.firm_prod_network.nodes[code]['Firm_Code']
# for code in self.firm_prod_network.predecessors(
# pro_firm_prod_code)
# if self.firm_prod_network.nodes[code][
# 'Product_Code'] == di_supp_prod.code]
# lst_cand = self.model.a_lst_total_firms.select([
# firm.is_prod_in_current_normal(di_supp_prod)
# and firm.code not in lst_current_supp_code
# for firm in self.model.a_lst_total_firms
# ])
# if len(lst_cand) > 0:
# select_cand = self.nprandom.choice(lst_cand)
# self.firm_network.graph.add_edges_from([
# (self.firm_network.positions[select_cand],
# self.firm_network.positions[pro_firm], {
# 'Product': di_supp_prod.code
# })
# ])
# # print(f"proactive add {select_cand.name} to "
# # f"{pro_firm.name} "
# # f"for {di_supp_node['Firm_Code']} "
# # f"{di_supp_node['Product_Code']}")
# # change capacity
# select_cand.dct_prod_capacity[di_supp_prod] -= 1
# break
# # nx.to_pandas_adjacency(G_Firm).to_csv('adj_g_firm_proactive.csv')
# draw network
# self.draw_network()