Skip to content

Instantly share code, notes, and snippets.

@AndersDJohnson
Last active June 5, 2019 13:33
Show Gist options
  • Save AndersDJohnson/4162390 to your computer and use it in GitHub Desktop.
Save AndersDJohnson/4162390 to your computer and use it in GitHub Desktop.
js cloning
// inspired by https://github.com/bestiejs/lodash/blob/master/lodash.js
// but supports cloning custom constructor instances
// still need to implement Date, RegExp
//If Object.create isn't already defined, we just do the simple shim, without the second argument,
//since that's all we need here
var Object_create = Object.create;
if (typeof Object_create !== 'function') {
Object_create = function(o) {
function F() {}
F.prototype = o;
return new F();
};
}
var arrayClass = '[object Array]';
function isArray (value) {
return toString.call(value) == arrayClass;
}
function clone(source, deep, sourceStack, cloneStack) {
// immediately return source with value semantics
if (source == null || typeof(source) !== 'object') {
return source;
}
// default to shallow
deep || (deep = false);
var isArr = isArray(source);
//make sure the returned object has the same type and prototype as the original
var cloned = isArr ? [] : Object_create(source.constructor.prototype);
if ( deep ) {
sourceStack || (sourceStack = []);
cloneStack || (cloneStack = []);
// check for circular references and return corresponding clone
var length = sourceStack.length;
while ( length-- ) {
if ( sourceStack[length] == source ) {
return cloneStack[length];
}
}
// add the source value to the stack of traversed objects
// and associate it with its clone
sourceStack.push(source);
cloneStack.push(cloned);
}
if ( isArr ) {
var length = source.length;
while ( length-- ) {
cloned[length] = deep ? clone( source[length], deep, sourceStack, cloneStack ) : source[length];
}
}
else {
for ( var key in source ) {
if ( ! source.hasOwnProperty(key) ) continue;
cloned[key] = deep ? clone( source[key], deep, sourceStack, cloneStack ) : source[key];
}
}
return cloned;
}
module.exports = clone
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment