J'ai trois grandes listes. Premier contient bitarrays (module bitarray 0.8.0) et les deux autres contiennent des tableaux d'entiers.Mémoire partagée en multitraitement
l1=[bitarray 1, bitarray 2, ... ,bitarray n]
l2=[array 1, array 2, ... , array n]
l3=[array 1, array 2, ... , array n]
Ces structures de données prennent un peu de RAM (~ 16Go au total).
Si je commence à 12 sous-processus en utilisant:
multiprocessing.Process(target=someFunction, args=(l1,l2,l3))
Est-ce que cela signifie que l1, l2 et l3 seront copiés pour chaque sous-processus ou seront les sous-processus partager ces listes? Ou pour être plus direct, vais-je utiliser 16 Go ou 192 Go de RAM? SomeFunction lira certaines valeurs de ces listes et effectuera ensuite certains calculs en fonction des valeurs lues. Les résultats seront renvoyés au processus parent. Les listes l1, l2 et l3 ne seront pas modifiées par someFunction.
Par conséquent, je suppose que les sous-processus n'ont pas besoin et ne copieraient pas ces énormes listes mais les partageraient plutôt avec le parent. Ce qui signifie que le programme prendrait 16 Go de RAM (quel que soit le nombre de sous-processus je commence) en raison de l'approche de copie sur écriture sous linux? Ai-je raison ou est-ce qu'il me manque quelque chose qui pourrait entraîner la copie des listes?
EDIT: Je suis toujours confus, après avoir lu un peu plus sur le sujet. D'une part, Linux utilise la copie sur écriture, ce qui signifie qu'aucune donnée n'est copiée. D'autre part, l'accès à l'objet changera son ref-count (je ne sais toujours pas pourquoi et qu'est-ce que cela signifie). Même ainsi, l'objet entier sera-t-il copié?
Par exemple, si je définis someFunction comme suit:
def someFunction(list1, list2, list3):
i=random.randint(0,99999)
print list1[i], list2[i], list3[i]
Est-ce que vous utilisez cette fonction signifie que L1, L2 et L3 sera entièrement copié pour chaque sous-processus?
Existe-t-il un moyen de vérifier cela? Après avoir lu un peu plus et surveillé l'utilisation totale de la mémoire du système pendant l'exécution des sous-processus, il semble que des objets entiers sont effectivement copiés pour chaque sous-processus. Et il semble que ce soit parce que la référence compte.
Le comptage de référence pour l1, l2 et l3 est réellement inutile dans mon programme. C'est parce que l1, l2 et l3 seront gardés en mémoire (inchangé) jusqu'à la sortie du processus parent. Il n'est pas nécessaire de libérer la mémoire utilisée par ces listes jusque-là. En fait, je sais avec certitude que le nombre de références restera supérieur à 0 (pour ces listes et tous les objets de ces listes) jusqu'à la sortie du programme. Maintenant, la question devient: comment puis-je m'assurer que les objets ne seront pas copiés dans chaque sous-processus? Puis-je désactiver le comptage des références pour ces listes et chaque objet de ces listes?
EDIT3 Juste une note supplémentaire. Les sous-processus n'ont pas besoin de modifier l1
, l2
et l3
ou tous les objets de ces listes. Les sous-processus doivent uniquement pouvoir référencer certains de ces objets sans que la mémoire soit copiée pour chaque sous-processus.
http://stackoverflow.com/questions/10721915/shared-memory-objects-in-python -multiprocessing Question similaire et votre réponse. – sean
Reaad par le biais et toujours pas sûr de la réponse. L'objet entier sera-t-il copié? Seulement une partie de l'objet? Une seule page contenant le refcount? Comment puis-je vérifier? – FableBlaze
En raison de copier-sur-écriture, je pense que vous ne devriez pas avoir à faire quelque chose de spécial. Pourquoi ne pas l'essayer? – NPE