मैं एक नक़ल मानचित्र में मानचित्र की प्रतिलिपि कैसे बना सकता हूँ? [डुप्लिकेट]


95

मैं जावास्क्रिप्ट में मैप को कैसे क्लोन / कॉपी करूं?

मुझे पता है कि एक सरणी का क्लोन कैसे बनाया जाता है, लेकिन मैं मैप को कैसे क्लोन / कॉपी करता हूं?

var myArray = new Array(1, 2, 3);
var copy    = myArray.slice();
// now I can change myArray[0] = 5; & it wont affect copy array

// Can I just do the same for map?
var myMap = new ?? // in javascript is it called a map?
var myMap = {"1": 1, "2", 2};
var copy  = myMap.slice(); 

3
ES6 आपको देता हैlet copy = {...myMap};
रिएक्टगुलर

जवाबों:


15

एक सरल तरीका (उथली प्रतिलिपि करने के लिए) स्रोत मानचित्र की प्रत्येक संपत्ति को लक्ष्य मानचित्र पर कॉपी करना है:

var newMap = {};
for (var i in myMap)
   newMap[i] = myMap[i];

नोट: newMap [i] बहुत अच्छी तरह से myMap [i] के समान वस्तु का संदर्भ हो सकता है


6
यह केवल एक उथली प्रतिलिपि है ... क्या होगा यदि myMap [i] एक नक्शा ही है?
स्टेफानो

1
स्टेफानो, आप यह कर सकते हैं कि यदि आप चाहें (यदि टाइपोफ़ के साथ कोई वस्तु है तो जांच करें, तो इसकी एक प्रति प्रस्तुत करें ... संभवतः उसी फ़ंक्शन को दोहराकर), लेकिन ध्यान रखें कि अब आपको चिंतित होना होगा उनके पूर्वज तत्व होने की संभावना उनमें है जो आपको एक अनंत पाश में डाल देगा। यदि आप वास्तव में एक गहरी प्रतिलिपि चाहते हैं, तो आप ऐसा करने के लिए पुस्तकालयों में देखना चाह सकते हैं।
लूटने

4
मुझे पता है, लेकिन मुझे लगता है कि आपको अपने जवाब में यह
स्टेफानो

6
यह नक्शा नहीं बल्कि एक वस्तु है। छोटा और सूद का अंतर। सीएफ developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/...
Helt

1
यह प्रत्येक संपत्ति की नकल नहीं करेगा जो आपके पास बस एक वस्तु के रूप में बसने और पाने वालों की पहुंच है
Amante Ninja

351

जावास्क्रिप्ट में मैप्स की शुरुआत के साथ, यह काफी सरल है, यह देखते हुए कि कंस्ट्रक्टर ने इसे एक स्वीकार्य स्वीकार किया है:

var newMap = new Map(existingMap)

यहाँ दस्तावेज़: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Map


4
ऊपर एक छोटा सा चेतावनी: इस तरह से एक नक्शा क्लोन करना, आह्वान करेगा Map.prototype.entriesऔर Map.prototype.set। इसका मतलब है कि: यदि आप एक वर्ग लिखते हैं जो मानचित्र का विस्तार करता है और इन दोनों विधियों में से किसी एक को अधिलेखित करता है, तो बस लेखन new ExtendedMap( extendedMapObj )कार्य नहीं करेगा यदि विस्तारित विधियां उन गुणों पर निर्भर करती हैं जो सुपर के लिए उपलब्ध नहीं हैं।

क्या यह गहरी क्लोन या सिर्फ उथले क्लोन है? मान लें कि मैंने ऑब्जेक्ट को मानों के रूप में नेस्टेड किया है
मेडो

लेकिन यह एक गहरी या उथली नकल करता है ??
योनातन नीर

5
यह उथली नकल करेगा, गहरा नहीं: jsfiddle.net/jormwe69
जाप

1
@PeterCoester सकते हैं हम कहते हैं कि के asymptotic var newMap = new Map(existingMap)है O(n)जहां nनक्शा कुंजी / मान जोड़े की संख्या है? मुझे लगता है कि क्लोनिंग ऑपरेशन स्थिर नहीं है O(1), जैसा कि आप कहते हैं, Map.prototype.entries हुड के नीचे कहा जाता है ...
tonix

10

जब आप जिस वस्तु के बारे में बात कर रहे हैं, उसका नक्शा बनाना बहुत सरल है, बस एक वस्तु है। एक भी नहीं है Mapकि आप देखना चाहिए, लेकिन एक वस्तु को कॉपी करने के लिए, बस उपयोग ES6 मेंObject.assign()

let map = {"a": 1, "b": 2}
let copy = Object.assign({}, map);

आप cloneDeep()लोधश से भी उपयोग कर सकते हैं

let copy = cloneDeep(map);

Object.assignडीप क्लोन के लिए चेतावनी: "यदि स्रोत मान किसी ऑब्जेक्ट का संदर्भ है, तो यह केवल संदर्भ मूल्य की प्रतिलिपि बनाता है।"
टॉम हेल

6

JQuery में एक वस्तु का विस्तार करने के लिए एक विधि है (दो वस्तुओं का विलय), लेकिन इस विधि का उपयोग किसी खाली वस्तु को प्रदान करके किसी वस्तु को क्लोन करने के लिए भी किया जा सकता है।

// Shallow copy
var newObject = jQuery.extend({}, oldObject);

// Deep copy
var newObject = jQuery.extend(true, {}, oldObject);

अधिक जानकारी jQuery प्रलेखन में पाई जा सकती है ।


3

में कुछ भी नहीं बनाया गया है।

या तो एक अच्छी तरह से परीक्षण की गई पुनरावर्ती संपत्ति कापियर का उपयोग करें या यदि प्रदर्शन कोई समस्या नहीं है, तो JSON को अनुक्रमित करें और फिर से एक नई वस्तु के लिए पार्स करें।


2

कोई अंतर्निहित क्लोन / कॉपी नहीं है। आप उथले या गहरी प्रति के लिए अपनी खुद की विधि लिख सकते हैं:

function shallowCopy(obj) {
    var result = {};
    for (var i in obj) {
        result[i] = obj[i];
    }
    return result;
}

function deepCopy(obj) {
    var result = {};
    for (var i in obj) {
        // recursion here, though you'll need some non-trivial logic
        // to avoid getting into an endless loop.
    }
    return result;
}

जावास्क्रिप्ट में सभी ऑब्जेक्ट गतिशील हैं, और उन्हें नए गुणों को सौंपा जा सकता है। एक "नक्शा" जैसा कि आप इसे संदर्भित करते हैं, वास्तव में सिर्फ एक खाली वस्तु है। एक सरणी भी एक वस्तु है, जैसे कि तरीके sliceऔर गुण जैसे length


समझ में नहीं आया कि आपके द्वारा लिखे गए 2 कार्यों में क्या अंतर है!
हसन ए यूसेफ

@ हसनयौफ अंतर लागू नहीं किया गया है; एक गहरी प्रतिलिपि में, आपको पुनरावृत्ति करना चाहिए (प्रत्येक बच्चे के लिए गहरी कोपी कॉल करें), लेकिन क्योंकि बच्चों में माता-पिता (उदाहरण के लिए window.window2 = विंडो) का संदर्भ हो सकता है, आप एक अंतहीन लूप में आए बिना उन संदर्भों की गहरी नकल नहीं कर सकते।
निकोल २

2

यदि आपको किसी मानचित्र की गहरी प्रतिलिपि बनाने की आवश्यकता है तो आप निम्नलिखित का उपयोग कर सकते हैं:

new Map(JSON.parse(JSON.stringify(Array.from(source))));

sourceमूल मैप ऑब्जेक्ट कहां है।

ध्यान दें कि यह उन सभी मामलों के लिए उपयुक्त नहीं हो सकता है जहाँ मानचित्र मान क्रमबद्ध नहीं हैं, अधिक जानकारी के लिए देखें: https://stackoverflow.com/a/122704/10583071


मैंने jsperf पर एक परीक्षण चलाया और पाया कि एक पुनरावृत्त दृष्टिकोण 10x तेज है: jsperf.com/deep-copy-map
Zack Burt

3
@ZackBurt दुख की बात है, आपका तेज़ प्रस्तावित विकल्प वास्तव deep copyमें लक्ष्य का नहीं बना है, Mapयह सिर्फ एक है shallow copy। शायद यह है कि यह इतनी जल्दी क्यों है?
अल्फांसो एम। गार्सिया एस्टोर्गा

@ AlfonsoM.GarcíaAstorga स्पष्ट करने के लिए धन्यवाद (तदनुसार तदनुसार)। आप सही हैं कि यह एक गहरी नकल नहीं है। लेकिन यह डेटा की <10kb के साथ एक तेज प्रतिलिपि है। अनुशंसित पूरक पढ़ने: v8.dev/blog/cost-of-javascript-2019#json
Zack Burt

1

मैंने देखा कि मानचित्र को विशेष उपचार की आवश्यकता है, इस प्रकार इस धागे में सभी सुझावों के साथ, कोड होगा:

function deepClone( obj ) {
    if( !obj || true == obj ) //this also handles boolean as true and false
        return obj;
    var objType = typeof( obj );
    if( "number" == objType || "string" == objType ) // add your immutables here
        return obj;
    var result = Array.isArray( obj ) ? [] : !obj.constructor ? {} : new obj.constructor();
    if( obj instanceof Map )
        for( var key of obj.keys() )
            result.set( key, deepClone( obj.get( key ) ) );
    for( var key in obj )
        if( obj.hasOwnProperty( key ) )
            result[key] = deepClone( obj[ key ] );
    return result;
}

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.