En Perl, lors de la copie de structures de données complexes (par exemple, des tableaux de tableaux, des hachages de hachages), il est important de comprendre la différence entre "copie superficielle" (shallow copy) et "copie profonde" (deep copy).
La copie superficielle crée un nouveau conteneur (par exemple, un tableau ou un hachage), mais les éléments en seront référencés aux mêmes objets que l'original. Cela peut entraîner un comportement inattendu : modifier des données dans la copie affectera l'original.
La copie profonde crée une structure complètement indépendante, en copiant récursivement tous les éléments imbriqués. Pour la copie profonde en Perl, on utilise souvent le module Storable ou [Clone]:
use Storable 'dclone'; my $original = { a => [1, 2, { b => 3 }] }; my $copy = $original; # Copie superficielle my $deep = dclone($original); # Copie profonde $copy->{a}[2]{b} = 42; # Change à la fois $copy et $original ! $deep->{a}[2]{b} = 99; # Change seulement $deep
La copie profonde garantit que les structures sont complètement isolées les unes des autres.
Quelle est la différence entre copier un tableau par l'affectation d'une variable et copier un tableau par référence ? Comment bien copier un tableau pour que les modifications dans l'un n'affectent pas l'autre ?
On répond souvent qu'il suffit d'affecter une référence : $copy = \@arr; — cependant, cela est faux, car les deux variables pointent vers le même tableau. Pour une copie indépendante, on utilise :
my @copy = @original; # Maintenant, les tableaux sont indépendants
Si des structures imbriquées doivent être copiées, une copie profonde est nécessaire, par exemple via Storable::dclone.
Histoire
Histoire
Histoire
Lors de la mise en œuvre de modèles d'e-mails pour des envois de masse, les structures d'origine avec des objets imbriqués étaient copiées par affectation, les modifications dans le texte du modèle "fugaient" entre les envois, ce qui entraînait l'envoi de messages obsolètes aux destinataires.