diff options
Diffstat (limited to 'railties/lib/vendor/thor-0.11.1/lib/thor/core_ext/ordered_hash.rb')
-rw-r--r-- | railties/lib/vendor/thor-0.11.1/lib/thor/core_ext/ordered_hash.rb | 102 |
1 files changed, 102 insertions, 0 deletions
diff --git a/railties/lib/vendor/thor-0.11.1/lib/thor/core_ext/ordered_hash.rb b/railties/lib/vendor/thor-0.11.1/lib/thor/core_ext/ordered_hash.rb new file mode 100644 index 0000000000..5e4ad5609f --- /dev/null +++ b/railties/lib/vendor/thor-0.11.1/lib/thor/core_ext/ordered_hash.rb @@ -0,0 +1,102 @@ +require 'forwardable' + +class Thor #:nodoc: + module CoreExt #:nodoc: + + if RUBY_VERSION >= '1.9' + class OrderedHash < ::Hash + end + else + # This class is based on the Ruby 1.9 ordered hashes. + # + # It keeps the semantics and most of the efficiency of normal hashes + # while also keeping track of the order in which elements were set. + # + class OrderedHash #:nodoc: + include Enumerable + + Node = Struct.new(:key, :value, :next, :prev) + + def initialize + @hash = {} + end + + def [](key) + @hash[key] && @hash[key].value + end + + def []=(key, value) + if node = @hash[key] + node.value = value + else + node = Node.new(key, value) + + if @first.nil? + @first = @last = node + else + node.prev = @last + @last.next = node + @last = node + end + end + + @hash[key] = node + value + end + + def delete(key) + if node = @hash[key] + prev_node = node.prev + next_node = node.next + + next_node.prev = prev_node if next_node + prev_node.next = next_node if prev_node + + @first = next_node if @first == node + @last = prev_node if @last == node + + value = node.value + end + + @hash.delete(key) + value + end + + def keys + self.map { |k, v| k } + end + + def values + self.map { |k, v| v } + end + + def each + return unless @first + yield [@first.key, @first.value] + node = @first + yield [node.key, node.value] while node = node.next + self + end + + def merge(other) + hash = self.class.new + + self.each do |key, value| + hash[key] = value + end + + other.each do |key, value| + hash[key] = value + end + + hash + end + + def empty? + @hash.empty? + end + end + end + + end +end |