हां, यह R <-(या =या ->) का उपयोग करते हुए सब ऑब्जेक्टिज़न है जो संपूर्ण ऑब्जेक्ट की प्रतिलिपि बनाता है । आप नीचे दिए अनुसार उपयोग कर सकते हैं tracemem(DT)और .Internal(inspect(DT))। data.tableसुविधाओं :=और set()जो कुछ के संदर्भ द्वारा असाइन आपत्ति वे पारित कर रहे हैं। इसलिए यदि वह वस्तु पहले कॉपी की गई थी (एक सबसाइनिंग <-या एक स्पष्ट द्वारा copy(DT)) तो यह वह कॉपी है जो संदर्भ द्वारा संशोधित हो जाती है।
DT <- data.table(a = c(1, 2), b = c(11, 12))
newDT <- DT
.Internal(inspect(DT))
# @0000000003B7E2A0 19 VECSXP g0c7 [OBJ,NAM(2),ATT] (len=2, tl=100)
# @00000000040C2288 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040C2250 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,12
# ATTRIB: # ..snip..
.Internal(inspect(newDT)) # precisely the same object at this point
# @0000000003B7E2A0 19 VECSXP g0c7 [OBJ,NAM(2),ATT] (len=2, tl=100)
# @00000000040C2288 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040C2250 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,12
# ATTRIB: # ..snip..
tracemem(newDT)
# [1] "<0x0000000003b7e2a0"
newDT$b[2] <- 200
# tracemem[0000000003B7E2A0 -> 00000000040ED948]:
# tracemem[00000000040ED948 -> 00000000040ED830]: .Call copy $<-.data.table $<-
.Internal(inspect(DT))
# @0000000003B7E2A0 19 VECSXP g0c7 [OBJ,NAM(2),TR,ATT] (len=2, tl=100)
# @00000000040C2288 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040C2250 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,12
# ATTRIB: # ..snip..
.Internal(inspect(newDT))
# @0000000003D97A58 19 VECSXP g0c7 [OBJ,NAM(2),ATT] (len=2, tl=100)
# @00000000040ED7F8 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040ED8D8 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,200
# ATTRIB: # ..snip..
ध्यान दें कि aवेक्टर की प्रतिलिपि कैसे बनाई गई थी (अलग-अलग हेक्स मान वेक्टर की नई प्रति इंगित करता है), भले ही aइसे बदला नहीं गया था। यहां तक कि पूरे bको कॉपी किया गया था, न कि केवल उन तत्वों को बदलने के लिए जिन्हें बदलने की आवश्यकता है। बड़े डेटा से बचने के लिए महत्वपूर्ण है, और क्यों :=और कैसे set()पेश किया गया data.table।
अब हमारी कॉपी के साथ newDTहम इसे संदर्भ द्वारा संशोधित कर सकते हैं:
newDT
# a b
# [1,] 1 11
# [2,] 2 200
newDT[2, b := 400]
# a b # See FAQ 2.21 for why this prints newDT
# [1,] 1 11
# [2,] 2 400
.Internal(inspect(newDT))
# @0000000003D97A58 19 VECSXP g0c7 [OBJ,NAM(2),ATT] (len=2, tl=100)
# @00000000040ED7F8 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040ED8D8 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,400
# ATTRIB: # ..snip ..
ध्यान दें कि सभी 3 हेक्स मान (स्तंभ बिंदुओं का वेक्टर, और प्रत्येक 2 कॉलम) अपरिवर्तित रहते हैं। तो यह वास्तव में बिल्कुल नहीं प्रतियां के साथ संदर्भ द्वारा संशोधित किया गया था।
या, हम DTसंदर्भ द्वारा मूल को संशोधित कर सकते हैं :
DT[2, b := 600]
# a b
# [1,] 1 11
# [2,] 2 600
.Internal(inspect(DT))
# @0000000003B7E2A0 19 VECSXP g0c7 [OBJ,NAM(2),ATT] (len=2, tl=100)
# @00000000040C2288 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 1,2
# @00000000040C2250 14 REALSXP g0c2 [NAM(2)] (len=2, tl=0) 11,600
# ATTRIB: # ..snip..
उन हेक्स मानों को मूल मूल्यों के समान हैं जिन्हें हमने DTऊपर देखा था । example(copy)उपयोग करने tracememऔर तुलना करने के लिए अधिक उदाहरणों के लिए टाइप करें data.frame।
Btw, अगर तुम tracemem(DT)तो DT[2,b:=600]तुम एक प्रति रिपोर्ट देखेंगे। यह पहली 10 पंक्तियों की एक प्रति है जो printविधि करती है। जब invisible()किसी फ़ंक्शन या स्क्रिप्ट में printकॉल किया जाता है , तो विधि को कॉल नहीं किया जाता है।
यह सब कार्यों के अंदर भी लागू होता है; यानी, :=और set()कार्यों के भीतर भी, लेखन पर कॉपी न करें। यदि आपको एक स्थानीय प्रतिलिपि को संशोधित करने की आवश्यकता है, तो x=copy(x)फ़ंक्शन की शुरुआत में कॉल करें । लेकिन, याद रखें data.tableबड़े डेटा (छोटे डेटा के लिए तेज प्रोग्रामिंग फायदे) के लिए है। हम जानबूझकर बड़ी वस्तुओं (कभी) की नकल नहीं करना चाहते हैं। परिणामस्वरूप हमें अंगूठे के सामान्य 3 * वर्किंग मेमोरी फैक्टर नियम के लिए अनुमति देने की आवश्यकता नहीं है। हमें केवल एक कॉलम जितना बड़ा (यानी 3 के बजाय 1 / ncol का वर्किंग मेमोरी फैक्टर) के रूप में कार्यशील मेमोरी की आवश्यकता है।
<-बजाय इसका उपयोग करने के=लिए आंतरिक रूप से इसका उपयोग करने की व्यापक रूप से वकालत की जाती है । लेकिन इसका मतलब यह है कि data.table मैनिप्युलेशन डेटा फ़्रेम मैनिपुलेशन के समान कार्य नहीं करेगा और इसलिए डेटा फ़्रेम में एक ड्रॉप-इन प्रतिस्थापन से बहुत दूर है।