Dans le domaine du calcul numérique, il existe depuis longtemps des simulations de particules en mouvement libre et de mouvements collectifs de particules brunes en mouvement. Cette fois, je vais appliquer cela à la simulation de l'infection à coronavirus. Il existe PSO en tant que simulation similaire, mais cette fois, j'ai fait référence à ces codes python. 【référence】 ・ À propos des paramètres d'optimisation des groupes de particules (PSO) ・ Méthode d'optimisation des groupes de particules enregistrés (PSO)
・ Explication du code ・ Dépendance au taux d'infection ・ Dépendance à la densité des particules ・ Dépendance au mouvement des particules
Le code complet est ci-dessous. ・ Collective_particles / snow.py Décrivez les principales parties du code. Les bibliothèques utilisées sont les suivantes
import numpy as np
import matplotlib.pyplot as plt
import random
import time
La définition de la valeur initiale est la suivante
PARTICLE_NO = 1000 #Nombre de particules
ITERATION = 200 #Nombre maximum de boucles S'arrête lorsque le nombre de personnes infectées atteint 0
MIN_X, MIN_Y = -100.0, -100.0 #Portée minimale au début de la recherche
MAX_X, MAX_Y = 100.0, 100.0 #Portée maximale au début de la recherche
recovery=30 #Guéri après une certaine période de temps
p=0.03 #probability of infecion
L'affichage du graphique, comme vous pouvez le voir à partir des résultats ci-dessus, ax1: informations sur la position des particules ax2: bleu; nombre normal, rouge; nombre d'infection, vert; graphique de fréquence du nombre de soins S'affiche comme suit. Les arguments sont le numéro du graphique, les informations de position, le temps écoulé, les valeurs r, g, b
def plot_particle(sk,positions,elt,r,g,b):
el_time = time.time()-start
fig, (ax1, ax2) = plt.subplots(2, 1, sharey=False,figsize=(8, 16))
for j in range(0,PARTICLE_NO):
x=positions[j]["x"]
y=positions[j]["y"]
c=positions[j]["c"]
s = 5**2 #La taille des particules
ax1.scatter(x, y, s, c, marker="o")
ax1.set_xlim([MIN_X, MAX_X])
ax1.set_ylim([MIN_Y, MAX_Y])
ax1.set_xlabel("x")
ax1.set_ylabel("y")
ax1.set_title("{:.2f}:InfectionRate;{:.2f} %".format(el_time,(PARTICLE_NO-b[-1])/PARTICLE_NO*100)) #Taux d'infection cumulé
ind = np.arange(len(elt)) # the x locations for the groups
width = 0.3 # the width of the bars
ax2.set_ylim([0, PARTICLE_NO])
ax2.set_title("{:.2f}:red_{} green_{} blue_{}".format(el_time,r[-1],g[-1],b[-1]))
rect1 = ax2.bar(ind, b,width, color="b")
rect2 = ax2.bar(ind+width, g, width, color="g")
rect3 = ax2.bar(ind+2*width, r,width, color="r")
plt.pause(0.1)
plt.savefig('./fig/fig{}_.png'.format(sk))
plt.close()
Cette fois, la logique principale a été poussée dans la fonction de mise à jour des informations de position des particules. Autrement dit, les attributs de l'objet particule sont définis comme suit.
attribut | valeur |
---|---|
Information de Lieu; | (x,y) |
Attribut infectieux; | (blue,red,green) |
Temps d'infection (écoulé depuis la valeur initiale); | t_time |
Indicateur d'historique d'infection; | s (1 infecté, 0 non infecté) |
position.append({"x": new_x, "y": new_y, "c": p_color, "t": t_time,"flag":s})
Utilisez la fonction suivante pour trouver le changement d'heure des variables ci-dessus. L'infection est jugée par la formule suivante. Si vous entrez un cercle avec un rayon de 20, il sera considéré comme un contact, et il sera évalué s'il sera ou non infecté avec une certaine probabilité p. En d'autres termes, ** ce rayon et la probabilité d'infection p déterminent la force de l'infection **.
if (x-x0[k])**2+(y-y0[k])**2 < 400 and random.uniform(0,1)<p:
Maintenant que nous avons défini l'objet particule comme ci-dessus, nous extrayons et assignons chaque variable. Autre chose, par souci de simplicité, la cicatrisation est ** automatiquement guérie après un certain temps **. Il est normal de guérir ici aussi, mais cela n'a pas besoin d'être détaillé ici car cela ne fait que compliquer l'événement. De plus, ** le mouvement des particules (mouvement des personnes) a été réglé sur une marche aléatoire ** en moyenne. C'est une approximation que les gens ne bougent pas autant. Par contre, il est possible de le faire bouger librement comme une simulation de mouvement moléculaire, mais je ne l'ai pas fait. Et ** l'hypothèse selon laquelle l'infection n'infecte pas une personne guérie **.
#Fonction de mise à jour de la position des particules
def update_position(positions):
x0 = []
y0 = []
for i in range(PARTICLE_NO):
c=positions[i]["c"]
t_time = positions[i]["t"] #Valeur initiale 0, heure de l'infection au moment de l'infection
k_time = time.time()-start #temps écoulé
s = positions[i]["flag"] #Aucune infection 0, infection: 1
if s == 1 and c == "red": #Si infecté
if k_time-t_time>recovery: #Guéri après une certaine période de temps
c = "blue"
positions[i]["c"] = "green"
positions[i]["flag"] = 1 #Cependant, les antécédents d'infection restent
if c == "red": #Obtenir des informations de localisation en cas d'infection rouge
x0.append(positions[i]["x"])
y0.append(positions[i]["y"])
position = []
for j in range(PARTICLE_NO):
x=positions[j]["x"]
y=positions[j]["y"]
c=positions[j]["c"]
s = positions[j]["flag"]
t_time = positions[j]["t"]
for k in range(len(x0)):
if (x-x0[k])**2+(y-y0[k])**2 < 400 and random.uniform(0,1)<p:
if s ==0:
c = "red"
t_time = time.time()-start
s = 1
positions[j]["flag"]=s
else:
continue
vx = 1*random.uniform(-1, 1)
vy = 1*random.uniform(-1, 1)
new_x = x + vx
new_y = y + vy
p_color = c
s=s
position.append({"x": new_x, "y": new_y, "c": p_color, "t": t_time,"flag":s})
return position, x0
La fonction principale est la suivante Le fait est qu'une particule est infectée par la valeur initiale; rouge, drapeau; 1, etc. D'autres particules sont disposées au hasard sans infection. Il y a une idée de placer la position de la première particule au centre, mais je voulais voir la transmission de l'infection à partir de différentes positions, alors j'ai choisi une position arbitraire. La fonction count_brg () compte simplement.
def main():
#Position initiale de chaque particule,la vitesse,
position = []
velocity = [] #Je n'utilise pas la vitesse cette fois
#Position initiale,Vitesse initiale
position.append({"x": random.uniform(MIN_X, MAX_X), "y": random.uniform(MIN_Y, MAX_Y), "c": "red", "t":0, "flag":1})
for s in range(1,PARTICLE_NO):
position.append({"x": random.uniform(MIN_X, MAX_X), "y": random.uniform(MIN_Y, MAX_Y), "c": "blue", "t": 0, "flag":0})
sk = 0
red=[]
green=[]
blue=[]
elapsed_time = []
while sk < ITERATION:
position, x0 = update_position(position)
r,g,b = count_brg(position)
red.append(r)
green.append(g)
blue.append(b)
el_time=time.time()-start
elapsed_time.append(el_time)
plot_particle(sk,position,elapsed_time,red,green,blue)
if x0==[]:
break
sk += 1
Premièrement, comment l'état de transmission de l'infection et le taux d'infection cumulé dans son ensemble changent-ils lorsque le taux d'infection p change? Dans l'exemple ci-dessus, le taux d'infection est p = 30%, le taux d'infection cumulé est de 100%, et on peut voir que l'infection s'est définitivement produite et se transmet comme un tsunami. Les pics d'infections étaient de 404 et 67,5 secondes. Dans ce cas, il semble qu'un débit de groupe tel que le débit de transmission puisse être défini, mais je l'ai en quelque sorte arrêté. D'autre part, lorsque le taux d'infection p = 5%, le taux d'infection cumulé a chuté à 92,20%, et l'état de transmission de l'infection est devenu visible en bleu comme indiqué ci-dessous, supprimé jusqu'au pic d'infection 235 et la position du pic s'est étendue à 178 secondes. De plus, lorsque le taux d'infection critique de la transmission ou non de l'infection = 3%, les résultats sont les suivants. En d'autres termes, c'est une image que la transmission d'infections comme le tsunami disparaît et se propage terriblement. Le pic d'infection était aussi bas que 117 et aussi long que 260 sec. Le taux d'infection cumulé a diminué à 52%. Dans le cas de ce taux d'infection, ce résultat de calcul se terminait également au milieu, mais il disparaissait parfois au stade initial avec presque aucune infection. En d'autres termes, ** Si vous pouvez réduire le taux d'infection en dessous d'un certain niveau (3% ou moins dans cette simulation) en utilisant un lavage des mains ou des masques, il est possible d'éliminer la transmission de l'infection. ** **
On considère que ces résultats ** indiquent qu'en contrôlant dans une certaine mesure les méthodes de communication telles que les masques, les câlins, les baisers et l'étiquette contre la toux, le taux d'infection cumulatif peut être réduit, bien qu'il puisse être prolongé. ça peut. Et si vous regardez attentivement cette simulation **, les particules bleues (personnes non infectées) dans la zone où se trouve une personne qui a guéri une fois sont protégées contre l'infection **, et la transmission de l'infection ne se propage pas vers l'intérieur. Autrement dit, ** la population de cette zone est robuste vis-à-vis de l'infection et évite rarement le risque d'infection. ** Autrement dit, on peut dire que ** l'immunité de masse acquise **. Cette immunité de masse peut être reformulée simplement comme ** empêchant la transmission de l'infection parce que le guérisseur réduit considérablement la densité d'individus non infectés dans la population **.
Un autre intérêt est de savoir si la sagesse commune de ** ne pas rassembler **, qui provoque généralement des annulations d'événements ou des annulations de rallye, est la bonne réponse. Ici, dans les conditions d'une probabilité d'infection de 30% et d'un temps de récupération de 30 secondes, la densité des particules a été modifiée pour voir la différence de comportement. Les résultats sont les suivants lorsque la dépendance de la densité des particules du taux d'infection est indiquée dans le tableau.
Densité de particules | 30 | 40 | 60 | 80 | 100 | 120 | 140 | 160 | 180 | 200 |
---|---|---|---|---|---|---|---|---|---|---|
Taux d'infection cumulé% | 3.33 | 27.5 | 8.33 | 40 | 33 | 49.17 | 67.86 | 70 | 91.67 | 96.5 |
Autrement dit, à une densité de 60 ou moins, la transmission de l'infection ne se produit pas et la transmission de l'infection commence à se produire à partir d'environ 80 / 200X200, de sorte que le taux d'infection cumulé commence à augmenter et atteint environ 100% à environ 200. A titre d'exemple, la simulation lorsque la région de transition est de 140 est représentée ci-dessous. La caractéristique était un pic unique lorsque la densité ci-dessus était suffisamment élevée, mais à ce niveau de densité, le pic de la personne infectée est plus doux et certains pics sont réfléchis, reflétant la fluctuation de densité de la distribution des particules. Montrer. Et, l'état de transmission de l'infection a du mal à surmonter la zone où la densité est faible, et on peut voir que ** parfois l'infection ne peut pas être transmise s'il y a trop d'espace **. En d'autres termes, la politique de ne pas cueillir a non seulement pour effet d'abaisser le taux d'infection cumulé en abaissant la densité globale **, mais aussi ** en agissant avec la politique de ne pas cueillir localement, la probabilité d'infection est Cela signifie qu'il peut être abaissé **.
Ensuite, vérifions si ** ne pas sortir ** est correct. Pour le moment, nous avons examiné comment cet effet affecte la transmission des infections et le taux d'infection cumulé lorsque le mouvement des particules est important. Lorsque la densité de particules est de 120, les résultats sont indiqués dans le tableau ci-dessous.
Mouvement des particules | 0 | 1 | 2 | 3 | 4 | 8 | 16 |
---|---|---|---|---|---|---|---|
Taux d'infection cumulé% | 10 | 49.17 | 54.17 | 83.33 | 79.17 | 65.83 | 74.17 |
D'après cette évaluation, il n'y a presque pas d'infection à cette densité à l'arrêt. D'autre part, on peut voir que le taux d'infection cumulatif augmente lorsqu'il y a un mouvement de particules, et le taux d'infection cumulé a tendance à augmenter à mesure que l'intensité augmente. On peut imaginer que cela surmonte simplement l'écart qui empêche la transmission de l'infection par l'exercice comme décrit ci-dessus. Un exemple typique d'une simulation réelle est le suivant. Comme vous pouvez l'imaginer à partir de cette simulation, vous pouvez voir que l'infection s'est propagée sur un espace légèrement large. En d'autres termes, on constate que ** ne pas sortir ** est aussi un acte de diminution du risque d'infection. Ce modèle de particules en mouvement peut également être simulé en considérant diverses situations qui imitent le monde réel, mais cette fois, c'est à ce point.
・ J'ai essayé de jouer en simulant une infection corona ・ ** La conclusion est que si les gens ne se rassemblent pas et que le taux d'infection peut être réduit en dessous d'un certain niveau (3% ou moins dans cette simulation) en utilisant bien le lavage des mains et les masques, il est possible d'éviter la transmission de l'infection par lui-même ** Obtenu ・ Il a été constaté que si le taux d'infection est réduit en ne rassemblant pas, ne se masquant pas, ne se lavant pas les mains, etc., il faut du temps pour mettre fin à l'infection, mais le taux d'infection cumulatif peut être réduit. ・ Pour vérifier l'effet de ne pas sortir, il a été constaté que le taux d'infection cumulatif augmente lors de l'exercice. ・ À haute densité, la transmission est similaire à la propagation des ondulations qui font tomber des gouttelettes d'eau. ・ S'il y a une faible densité mais une transmission de l'infection, la zone où coexistent les personnes guéries et non infectées s'étendra, mais cette zone est robuste contre l'infection et peut être considérée comme un état immunitaire de masse.
・ Si cette simulation est effectuée à une plus grande échelle, elle peut être étendue pour imiter une ville réelle, donc je vais essayer de calculer avec une puissance de feu un peu plus élevée. Au fait, j'ai utilisé Jetson-nano cette fois-ci, mais j'ai pu calculer jusqu'à 1000 sans aucun problème.