Opinions of preinitialize system and overridiing #new

T

Trans

#--
# Preinitialize
#
# Copyright (c) 2005 Thomas Sawyer
#
# Ruby License
#
# This module is free software. You may use, modify, and/or
redistribute this
# software under the same terms as Ruby.
#
# This program is distributed in the hope that it will be useful, but
WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS
# FOR A PARTICULAR PURPOSE.
#
#
#
==========================================================================
# Revision History ::
#
--------------------------------------------------------------------------
# 05.08.26 trans Created
#
==========================================================================
#++

#:title: Preinitialize
#
# This is an object preinitialize system, which provides
# an elegant way to initialize an object allowing the
# class to provide additional default structure to an
# object prior to calling initialize.
#
# In effect it does two things after allocating the object
# but prior to initializing it.
#
# First, it calls the class method #default_instance_variables,
# which returns a hash and by default returns the hash
# stored in @@default_instance_variables. It uses this to
# pre-define instance variables.
#
# Then it goes to the top of the class hierarchy and works
# it's way down calling #preinitialize if defined.
# WARNING! It is rather useless to use <tt>super</tt>
# inside a preinitialize hook.
#
# class X
# attr_reader :a, :b
#
# default_instance_values[:a] = 42
#
# def preinitialize
# @b = 23
# end
# end
#
# x = X.new
# x.a #=> 42
# x.b #=> 23
#
# If neded the original new method has been aliased, albeit
# <tt>postinitialize_new</tt> is probably a bit of a misnomer.
#

class Class

def default_instance_variables
@@default_instance_variables ||= {}
end

alias :postinitialize_new :new

def new(*args,&blk)
o = allocate

if respond_to?:)default_instance_variables)
default_instance_variables.each{ |k,v|
o.instance_variable_set( "@#{k.to_s.gsub(/\W$/,'')}",v )
}
end

a = ancestors
until a.empty?
m = a.pop
if m.private_instance_methods.include?('preinitialize') or
m.public_instance_methods.include?('preinitialize')
im = instance_method('preinitialize')
im.arity == 0 ? im.bind(o).call : im.bind(o).call(*args, &blk)
end
end

o.send:)initialize, *args, &blk)

return o
end
end
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
474,444
Messages
2,571,709
Members
48,796
Latest member
Greg L.
Top