Kopiranje

Sklicevanje na isti objekt lahko vpliva na težavnost branja programa, saj imajo lahko spremembe, ki jih naredimo na enem mestu, nepričakovane učinek na drugem mestu. Tako je težko slediti vsem spremenljivkam, ki se sklicujejo na določeni objekt.

Kopiranje objekta pogosto predstavlja alternativo sklicevanju na objekt. Modul copy vsebuje funkcijo z imenom copy, ki lahko podvoji kateri koli objekt:

>>> import copy
>>> t1 = Tocka(4, 3)
>>> t2 = copy.copy(t1)
>>> t1 is t2
False
>>> iste_koordinate(t1, t2)
True

Ko uvozimo modul copy, lahko uporabimo funkcijo copy, da ustvarimo nov objekt Tocka. Točki t1 in t2 nista ista točka, vendar vsebujeta enake podatke.

Za kopiranje preprostih objektov, kot na primer Tocka, ki ne vsebujejo nobenih vgrajenih objektov, funkcija copy zadostuje. To imenujemo plitvo kopiranje (ang. shallow copying).


Za objekte, kot na primer Pravokotnik, ki vsebuje sklic na objekt Tocka, pa funkcija copy ne zadostuje, ker kopira sklic na objekt Tocka, zato se stari in novi pravokotnik, sklicujeta na isti objekt Tocka.

Če ustvarimo pravokotnik okvir1 na običajen način in nato ustvarimo njegovo kopijo okvir2 z uporabo funkcije copy, potem diagram izgleda takole:

To skoraj zagotovo ni tisto, kar si želimo. V tem primeru klic metode spremeni na enem izmed objektov Pravokotnik ne bi vplival na drugi pravokotnik, klic metode premakni pa bi vplival na oba pravokotnika! Takšno obnašanje je zmedeno in nagnjeno k napakam. Plitva kopija je ustvarila sklic na objekt Tocka, ki predstavlja oglišče pravokotnika.

Na srečo modul copy vsebuje funkcijo z imenom deepcopy, ki ne kopira samo objektov, temveč tudi vgrajene objekte. Zato vas ne bo presentilo, da takšno kopiranje imenujemo globoko kopiranje (ang. deep copy).

>>> okvir2 = copy.deepcopy(okvir1)
Sedaj sta okvir1 in okvir2 popolnoma ločena objekta.