Подтвердить что ты не робот

Когда использовать dup и когда использовать клон в Ruby?

В чем разница между методами Ruby dup и clone? описывает разницу в поведении dup и clone. Но когда я должен использовать dup, и когда следует использовать clone вместо?

Примеры из реальных проектов, которые обсуждают, почему они использовали dup, а не клон, или наоборот, были бы идеальны для этого вопроса.

Альтернативно, объяснение того, почему существуют два разных метода, было бы полезно. Это может относиться к утверждениям создателей Ruby или к рассмотрению таких методов, как dup и clone на языках, которые влияют на Ruby.

4b9b3361

Ответ 1

Верно, что clone копирует состояние frozen объекта, а dup не выполняет:

o = Object.new
o.freeze

o.clone.frozen?
#=> true

o.dup.frozen?
#=> false

clone также скопирует одноэлементные методы объекта, а dup не будет:

o = Object.new
def o.foo
  42
end

o.clone.respond_to?(:foo)
#=> true

o.dup.respond_to?(:foo)
#=> false

Это приводит меня к предположению, что clone иногда понимается как предоставление "более глубокой" копии, чем dup. Вот несколько цитат по теме:

Комментировать ActiveRecord::Base#initialize_dup из Rails 3:

Duped объекты не имеют назначенного идентификатора и рассматриваются как новые записи. Заметка что это "мелкая" копия, поскольку она копирует атрибуты объекта только, а не его ассоциации. Степень "глубокой" копии - это приложение и поэтому оставляется для применения в соответствии с к его потребности.

Статья о глубоких копиях в Ruby:

Можно упомянуть еще один метод clone. Метод clone делает одно и то же, что и dup, с одним важным отличием: он ожидал, что объекты переопределяют этот метод тем, который может делать глубокие копии.

Но опять же, theres deep_dup в Rails 4:

Возвращает глубокую копию объекта, если он дублируется. Если он не дублируется, возвращает self.

, а также ActiveRecord::Core#dup и #clone в Rails 4:

clone - Идентичный метод клонирования Ruby. Это "мелкая" копия. Будьте предупреждены, что ваши атрибуты не копируются. [...] Если вам нужна копия хэша атрибутов, используйте метод #dup.

Это означает, что здесь слово dup используется снова для обращения к глубокому клону. Насколько я вижу, в сообществе, по-видимому, нет консенсуса, за исключением того, что вы должны использовать clone и dup в случае, когда вам нужен конкретный побочный эффект одного из них.

Наконец, я вижу dup гораздо чаще в коде Ruby, чем clone. Я до сих пор не использовал clone, и я не буду, пока я явно не буду.

Ответ 2

Оба DUP и CLONE могут использоваться для создания мелкой копии объекта. Оба экземпляра копируют переменные экземпляра obj. Но мы должны быть избирательными в их использовании.

Немного разница между ними

1) CLONE копирует состояние FROZEN и TAINTED объекта, где, поскольку DUP копирует только состояние TAINTED объекта.

2) С помощью CLONE вы можете копировать любые однотонные методы объекта, но DUP не поддерживает это.

CLONE используется для дублирования объекта, включая его внутреннее состояние, DUP обычно использует класс объекта-потомка для создания нового экземпляра.

У меня был какой-то горький опыт при использовании DUP для дублирования строки ActiveRecord, это закончилось тем, что утеряло оригинал, который отлично работал с CLONE.

Как я в замешательстве, я понял это в Статья с открытым исходным кодом широко открыта