Комментарии 42
А o&&{} сделано для того чтобы в r null получить, если он там есть? а если нет, то будет {}.
0
Можно добавить проверку на null, а заодно — сократить:
function dup(o,i,r) {
r=o;
if(r && typeof o == "object") {
r = o instanceof Array ? [] : {};
for(i in o)
if(o.hasOwnProperty(i))
r[i] = dup(o[i]);
}
return r
}
// 136
function dup(o,i,r){r=o;if(r&&typeof o=="object"){r=o instanceof Array?[]:{};for(i in o)if(o.hasOwnProperty(i))r[i]=dup(o[i])}return r}
// отказ от ie8, 134 символа:
function dup(o,i,r){r=o;if(r&&typeof o=="object"){r=Array.isArray(o)?[]:{};for(i in o)if(o.hasOwnProperty(i))r[i]=dup(o[i])}return r}
+2
Даже не 136 и 134, а 135 и 133 :)
А с отказом от IE8, заодно заменив название функции на «c», наконец-то впихиваем ровно в твит ещё и минимальную проверку на кольца:
Спасибо!
А с отказом от IE8, заодно заменив название функции на «c», наконец-то впихиваем ровно в твит ещё и минимальную проверку на кольца:
function c(o,i,r){r=o;if(r&&typeof o=="object"){r=Array.isArray(o)?[]:{};for(i in o)if(o.hasOwnProperty(i))r[i]=o[i]===o?r:c(o[i])}return r}
Спасибо!
+2
Можно сделать что-то типа такого и даже не отказываться от IE =)
function c(o,i,r){if(o&&typeof o=="object"){r=o instanceof Array?[]:{};for(i in o)o.hasOwnProperty(i)?r[i]=o[i]===o?r:c(o[i]):0}return r||o}
+1
Круто! Добавил в пост!
Спасибо :)
Вот, кстати, 140байтные js'ки: 140byt.es/ (в т.ч. неглубокое копирование).
Ну как, может, выложить?
Только там надо под WTFPL лицензией выкладывать.
Спасибо :)
Вот, кстати, 140байтные js'ки: 140byt.es/ (в т.ч. неглубокое копирование).
Ну как, может, выложить?
Только там надо под WTFPL лицензией выкладывать.
0
Я не против этой лицензии.
Только проверьте последний код, а то я в нём не уверен)
Только проверьте последний код, а то я в нём не уверен)
0
Ок, приеду домой проверю :)
Демка не поломалась, так что, скорее всего, работает.
Демка не поломалась, так что, скорее всего, работает.
0
Пришла в голову безумная мысль, но я в дороге — проверить не могу. Такая конструкция имеет право на жизнь?
r = new o.constructor()
?
r = new o.constructor()
?
0
new o.constructor() даже работает в какой-то мере: прототип и конструктор перекидывает в клона. Правда, Date, Number, String и Boolean так и остались за бортом: естественно, создаётся новый объект.
Я только не могу понять идеологической верности/неверности данного решения: с одной стороны, часть проблем решается, с другой — ведёт себя совсем не так, как привыкли пользователи jQuery, да и другая часть проблем добавляется.
Вот и думаю теперь, что с этим делать…
Я только не могу понять идеологической верности/неверности данного решения: с одной стороны, часть проблем решается, с другой — ведёт себя совсем не так, как привыкли пользователи jQuery, да и другая часть проблем добавляется.
Вот и думаю теперь, что с этим делать…
0
Ну, заслал: gist.github.com/2369704
И твитнул: https://twitter.com/#!/l_x_y_d/status/190521513227722752
Твиттер для этого завёл наконец >_<
Насколько я понял, теперь надо ждать реакции.
И твитнул: https://twitter.com/#!/l_x_y_d/status/190521513227722752
Твиттер для этого завёл наконец >_<
Насколько я понял, теперь надо ждать реакции.
0
Не понятно, зачем тут конструкция
Ну и для лаконичности :)
o[i] === o ?
— как элемент объекта/массива может быть равен самому объекту/массиву?Ну и для лаконичности :)
function c(o,p,y){if(o&&typeof o=="object"){p=o instanceof Array?[]:{};for(y in o)o.hasOwnProperty(y)?p[y]=c(o[!p||y]):0}return p||o}
+1
Может быть равен, там же всё — ссылки.
Отличная идея со словом copy :)
Отличная идея со словом copy :)
0
Может быть равенПример? У меня не получилось такой найти, везде false.
function c(o,p,y){
if(o&&typeof o=="object"){
p=o instanceof Array?[]:{};
for(y in o){
if(o.hasOwnProperty(y)){
if(o[y] === o){
p[y] = p
console.log(y + ' true')
} else {
p[y] = c(o[y])
console.log(y + ' false')
}
}
}
}
return p||o
}
c({a:1,b:2,c:{c1:1,c2:{c3:"asdasd", c4: 2*2}}}) // false
c([1,2,3,[4,5,6,[7,8,9]]]) // false
c([1,1,[1,1,[1,1]]]) // false
0
В такой записи, конечно! Но можно же и потом присвоить: x.field = x;
Просто я эту шткуку делал, когда мне нужно было скопировать структуру, где такие бек-референсы были. Вернее, могли быть.
Ну хорошо, может это и не частый случай :)
Просто я эту шткуку делал, когда мне нужно было скопировать структуру, где такие бек-референсы были. Вернее, могли быть.
Ну хорошо, может это и не частый случай :)
0
Как вариант тогда:
Сжатый вариант на 9 символов короче:
Ну или если забить на __proto__, то вот самый короткий вариант:
function dup(object, copy) {
if(typeof object == 'object') {
copy = object instanceof Array ? [] : object && {};
Object.keys(object).forEach(function(key) {
copy[key] = dup(object[key]);
});
}
return copy || object;
}
var object = {
a: {
b: {
c: 1
}
}
}
dup(object);
Сжатый вариант на 9 символов короче:
function dup(o,c){if(typeof o=='object'){c=o instanceof Array?[]:o&&{};Object.keys(o).map(function(k){c[k]=dup(o[k])})}return c||o}
Ну или если забить на __proto__, то вот самый короткий вариант:
var copy = Object.create(object);
0
Это будет работать в браузерах, но есть ещё и IE.
+1
Во-первых, IE8-. Во-вторых, никто не говорил о том, что запрещено использование ES5. В-третьих, тот же map не так сложно реализовать чтобы от него отказаться:
(function($) {
'use strict';
if(!$.map) {
$.map = function(fn, object) {
var i = -1, length = this.length, array = [];
while(i++ < length) {
if(i in this)
array.push(fn.call(object, this[i], i, this));
}
return array;
};
}
})(Array.prototype);
0
А можно в пост добавить?
0
r=o можно в if засунуть, -2 символа.
0
Не выйдет: тогда надо присваивание в скобки обернуть, а это как раз те самые два символа заберёт обратно. А жаль — можно было бы вернуть поддержку IE8 за счёт этого :(
0
> var a = true, b = false
> if (b=a&&typeof a=="boolean") 1
> 1
> b
> true
> a
> true
0
Array.isArray(o) есть такая штука.
0
Было:
o.hasOwnProperty(i)?r[i]=o[i]===o?r:c(o[i]):0
Стало:
o.hasOwnProperty(i)&&r[i]=o[i]===o?r:c(o[i])
o.hasOwnProperty(i)?r[i]=o[i]===o?r:c(o[i]):0
Стало:
o.hasOwnProperty(i)&&r[i]=o[i]===o?r:c(o[i])
0
Обновил пост: добавил ссылку на ещё один вариант, сделанный уже не из спортивного интересу, а для боевого применения. Метод должен быть практически универсальным: работает с датами, стандартными обёртками Boolean, String и т.д., полностью разруливает циклы и даже не боится наличия в хеше ключа hasOwnProperty.
Естественно, в твит (даже в два) уже не влезает, однако, думаю, что именно этот вариант я и буду использовать на практике.
Естественно, в твит (даже в два) уже не влезает, однако, думаю, что именно этот вариант я и буду использовать на практике.
0
Для чего нужно
o.hasOwnProperty(i)
, если мы из него же и извлекаем эту i
?0
В стародавние времена люди змейку на ассемблере писали — кто компактней, а сейчас js :-) Люди не меняются.
Непонятно функционал для клона не включили в стандарт, хотя бы без рекурсии.
Непонятно функционал для клона не включили в стандарт, хотя бы без рекурсии.
0
Зарегистрируйтесь на Хабре, чтобы оставить комментарий
DeepClone на javascript, который можно твитнуть