[前][次][番号順一覧][スレッド一覧]

ruby-changes:19661

From: drbrain <ko1@a...>
Date: Mon, 23 May 2011 08:46:18 +0900 (JST)
Subject: [ruby-changes:19661] drbrain:r31706 (trunk): * lib/ostruct.rb: Improve documentation. Patch by Franklin Webber.

drbrain	2011-05-23 08:46:08 +0900 (Mon, 23 May 2011)

  New Revision: 31706

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=31706

  Log:
    * lib/ostruct.rb:  Improve documentation.  Patch by Franklin Webber.
      [Ruby 1.9 - Bug #4761]

  Modified files:
    trunk/ChangeLog
    trunk/lib/ostruct.rb

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 31705)
+++ ChangeLog	(revision 31706)
@@ -1,3 +1,8 @@
+Mon May 23 08:45:55 2011  Eric Hodel  <drbrain@s...>
+
+	* lib/ostruct.rb:  Improve documentation.  Patch by Franklin Webber.
+	  [Ruby 1.9 - Bug #4761]
+
 Mon May 23 08:35:24 2011  Eric Hodel  <drbrain@s...>
 
 	* hash.c:  Improve documentation of Hash#key.  Patch by Utkarsh
Index: lib/ostruct.rb
===================================================================
--- lib/ostruct.rb	(revision 31705)
+++ lib/ostruct.rb	(revision 31706)
@@ -9,40 +9,92 @@
 #
 
 #
-# OpenStruct allows you to create data objects and set arbitrary attributes.
-# For example:
+# An OpenStruct is a data structure, similar to a Hash, that allows the
+# definition of arbitrary attributes with their accompanying values. This is
+# accomplished by using Ruby's metaporgramming to define methods on the class
+# itself.
 #
+# == Examples:
+#
 #   require 'ostruct'
 #
-#   record = OpenStruct.new
-#   record.name    = "John Smith"
-#   record.age     = 70
-#   record.pension = 300
+#   person = OpenStruct.new
+#   person.name    = "John Smith"
+#   person.age     = 70
+#   person.pension = 300
 #
-#   puts record.name     # -> "John Smith"
-#   puts record.address  # -> nil
+#   puts person.name     # -> "John Smith"
+#   puts person.age      # -> 70
+#   puts person.address  # -> nil
 #
-# It is like a hash with a different way to access the data.  In fact, it is
-# implemented with a hash, and you can initialize it with one.
+# An OpenStruct employs a Hash internally to store the methods and values and
+# can even be initialized with one:
 #
-#   hash = { "country" => "Australia", :population => 20_000_000 }
-#   data = OpenStruct.new(hash)
+#   country_data = { :country => "Australia", :population => 20_000_000 }
+#   australia = OpenStruct.new(country_data)
+#   p australia   # -> <OpenStruct country="Australia" population=20000000>
 #
-#   p data        # -> <OpenStruct country="Australia" population=20000000>
+# You may also define the hash in the initialization call:
 #
+#   australia = OpenStruct.new(:country => "Australia", :population => 20_000_000)
+#   p australia   # -> <OpenStruct country="Australia" population=20000000>
+#
+# Hash keys with spaces or characters that would normally not be able to use for
+# method calls (e.g. ()[]*) will not be immediately available on the
+# OpenStruct object as a method for retrieval or assignment, but can be still be
+# reached through the Object#send method.
+#
+#   measurements = OpenStruct.new("length (in inches)" => 24)
+#   measurements.send("length (in inches)")  # -> 24
+#
+#   data_point = OpenStruct.new(:queued? => true)
+#   data_point.queued?                       # -> true
+#   data_point.send("queued?=",false)
+#   data_point.queued?                       # -> false
+#
+# Removing the presence of a method requires the execution the delete_field
+# method as setting the property value to +nil+ will not remove the method.
+#
+#   first_pet = OpenStruct.new(:name => 'Rowdy', :owner => 'John Smith')
+#   first_pet.owner = nil
+#   second_pet = OpenStruct.new(:name => 'Rowdy')
+#
+#   first_pet == second_pet   # -> false
+#
+#   first_pet.delete_field(:owner)
+#   first_pet == second_pet   # -> true
+#
+#
+# == Implementation:
+#
+# An OpenStruct utilizes Ruby's method lookup structure to and find and define
+# the necessary methods for properties. This is accomplished through the method
+# method_missing and define_method.
+#
+# This should be a consideration if there is a concern about the performance of
+# the objects that are created. As there is much more overhead in the setting
+# of these properties compard to utilizing a Hash or a Struct.
+#
 class OpenStruct
   #
-  # Create a new OpenStruct object.  The optional +hash+, if given, will
-  # generate attributes and values.  For example.
+  # Creates a new OpenStruct object.  By default, the resulting OpenStruct
+  # object will have no attributes.
   #
+  # The optional +hash+, if given, will generate attributes and values.
+  # For example:
+  #
   #   require 'ostruct'
   #   hash = { "country" => "Australia", :population => 20_000_000 }
   #   data = OpenStruct.new(hash)
   #
   #   p data        # -> <OpenStruct country="Australia" population=20000000>
   #
-  # By default, the resulting OpenStruct object will have no attributes.
+  # You may also define the hash in the initialization call:
   #
+  #   australia = OpenStruct.new(:country => "Australia",
+  #                              :population => 20_000_000)
+  #   p australia   # -> <OpenStruct country="Australia" population=20000000>
+  #
   def initialize(hash=nil)
     @table = {}
     if hash
@@ -59,14 +111,43 @@
     @table = @table.dup
   end
 
+  #
+  # Provides marshalling support for use by the Marshal library. Returning the
+  # underlying Hash table that contains the functions defined as the keys and
+  # the values assigned to them.
+  #
+  #    require 'ostruct'
+  #
+  #    person = OpenStruct.new
+  #    person.name = 'John Smith'
+  #    person.age  = 70
+  #
+  #    person.marshal_dump # => { :name => 'John Smith', :age => 70 }
+  #
   def marshal_dump
     @table
   end
+
+  #
+  # Provides marshalling support for use by the Marshal library. Accepting
+  # a Hash of keys and values which will be used to populate the internal table
+  #
+  #    require 'ostruct'
+  #
+  #    event = OpenStruct.new
+  #    hash = { 'time' => Time.now, 'title' => 'Birthday Party' }
+  #    event.marshal_load(hash)
+  #    event.title # => 'Birthday Party'
+  #
   def marshal_load(x)
     @table = x
     @table.each_key{|key| new_ostruct_member(key)}
   end
 
+  #
+  # #modifiable is used internally to check if the OpenStruct is able to be
+  # modified before granting access to the internal Hash table to be augmented.
+  #
   def modifiable
     begin
       @modifiable = true
@@ -77,6 +158,11 @@
   end
   protected :modifiable
 
+  #
+  # new_ostruct_member is used internally to defined properties on the
+  # OpenStruct. It does this by using the metaprogramming function
+  # define_method for both the getter method and the setter method.
+  #
   def new_ostruct_member(name)
     name = name.to_sym
     unless self.respond_to?(name)
@@ -104,8 +190,15 @@
   end
 
   #
-  # Remove the named field from the object.
+  # Remove the named field from the object. Returning the value that the field
+  # contained if it has defined.
   #
+  #   require 'ostruct'
+  #
+  #   person = OpenStruct.new('name' => 'John Smith', 'age' => 70)
+  #
+  #   person.delete_field('name')  # => 'John Smith'
+  #
   def delete_field(name)
     sym = name.to_sym
     @table.delete sym
@@ -144,7 +237,9 @@
   protected :table
 
   #
-  # Compare this object and +other+ for equality.
+  # Compares this object and +other+ for equality.  An OpenStruct is equal to
+  # +other+ when +other+ is an OpenStruct and the two object's Hash tables are
+  # equal.
   #
   def ==(other)
     return false unless(other.kind_of?(OpenStruct))

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]