Module: DeepDup
- Defined in:
- lib/deep_dup.rb,
lib/deep_dup/version.rb,
lib/deep_dup/core_ext/object.rb
Overview
Deep duplicate any object. Some objects cannot be dupped like nil
, false
, true
, numbers, symbols and method objects. In those cases return themselvese.
Defined Under Namespace
Modules: CoreExt
Constant Summary collapse
- VERSION =
Version number, happy now?
'0.0.2'
Class Method Summary collapse
-
.cache_object(object, new_object, cache) {|new_object| ... } ⇒ Array, Hash
Prevent infinite recursion on recursive data structures.
-
.deep_dup(object, cache = {}) ⇒ Object
Deep duplicate any object.
Class Method Details
.cache_object(object, new_object, cache) {|new_object| ... } ⇒ Array, Hash
Prevent infinite recursion on recursive data structures.
Imagine an array that has only one item which is a reference to itself. When entering this method, the cache is empty so we create a new array and map the original object’s id to this newly created object.
We then give control back to deep_dup
so that it can go on and do the adding, which will call itself with the same array and enter this method again.
But this time, since the object is the same, we know the duplicate object because we stored in in our little cache. So just go ahead and return it otherwise it would result in an infinite recursion.
90 91 92 93 94 95 96 97 98 99 |
# File 'lib/deep_dup.rb', line 90 def self.cache_object(object, new_object, cache) object_id = object.object_id dupped_object = cache[object_id] # Did we already visit this object? return dupped_object if dupped_object # Yes, return it, prevent overflow. cache[object_id] = new_object # Map the original object id to the new object. yield(new_object) # Let +deep_dup+ do the job. new_object # Just return it to +deep_dup+. end |
.deep_dup(object, cache = {}) ⇒ Object
Deep duplicate any object.
46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 |
# File 'lib/deep_dup.rb', line 46 def self.deep_dup(object, cache = {}) # rubocop:disable Metrics/MethodLength case object when String object.dup when nil, false, true, Numeric, Symbol, Method object when Array cache_object(object, [], cache) do |new_object| object.each do |item| new_object << deep_dup(item, cache) end end when Hash cache_object(object, {}, cache) do |new_object| object.each do |key, value| new_object[deep_dup(key, cache)] = deep_dup(value, cache) end end else # Object, Class object.dup end end |