[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.ruby

MyClass.to_another_class

Shea Martin

4/11/2006 7:29:00 PM

Consider the following:

######################################################
#!ruby

class A
def initialize
@name = 'A'
end
end

class B < A
def initialize
super
@name = 'B'
@data = Array.new
end
def set_text( p_text )
@text = p_text
end
def B.from_a( p_A )
l_rslt = B.new
l_rslt.data = Array.new
end

private
def data=( p_new_array )
@data = p_new_array
end
end

a = A.new
b = B.from_a( a )

exit 0
#############################################################

My B.from_a does not compile, as 'data' is not a public member. My
quesiton is how can I keep restricted access to @data, but allow my
from_a method to work?

Or is there a better way to accomplish this? I don't want to have a
A.to_b method, as that introduces double coupling.

Thanks,

~S
4 Answers

Shea Martin

4/11/2006 7:39:00 PM

0

Here is an example with reasons as to why I would like to do this:

Consider the following:

######################################################
#!ruby

class X
attr_reader :text
def initialize
@name = 'X'
@text = ""
end
def add_to_text( p_str )
@text += p_str
end
end

class Y < X
def initialize
super
@name = 'Y'
@arr = Array.new
end
def Y.from_x( p_X )
l_rslt = Y.new
l_rslt.text = p_X.text
end

private
def text=( p_text )
@text = p_text
end
end

x = X.new
y = Y.from_a( a )

exit 0


##################################################

When I need to specialize x by changing the type to y, I lose the data
store in @text. But I need to promote to gain the added features of Y.

Thanks,

~S

James Herdman

4/12/2006 4:05:00 AM

0

> class X
> attr_reader :text
> def initialize
> @name = 'X'
> @text = ""
> end
> def add_to_text( p_str )
> @text += p_str
> end
> end
>
> class Y < X
> def initialize
> super
> @name = 'Y'
> @arr = Array.new
> end
> def Y.from_x( p_X )
> l_rslt = Y.new
> l_rslt.text = p_X.text
> end
>
> private
> def text=( p_text )
> @text = p_text
> end
> end
>
> x = X.new
> y = Y.from_a( a )
>
> exit 0

I can't proporte to be a Ruby expert, but I'll give it my best shot.

First of all, I'm a bit confused by what you're hoping the effect of
Y.from_x() is. Are you hoping to return a new object of type Y? If
I'm not mistaken, you may need to explicitly return it. i.e.

def Y.from_x( p_X )
result = Y.new
result.text = p_X.text
return result
end

Now, the second line of this method is where I think your problem might
be. When I run your code, as is, in IRB, it freaks out. result.text
is calling the private method text(). Since private methods CANNOT be
invoked by an explicit receiver, you are violating this by saying
result.text(). Try removing the private condition, and I think you'll
be okay.

This is your new Y

class Y < X
def initialize
super
@name = 'Y'
@arr = Array.new
end

def Y.from_x( p_X )
l_rslt = Y.new
l_rslt.text = p_X.text
return l_rslt
end

def text=( p_text )
@text = p_text
end
end

irb(main):028:0> x = X.new
=> #<X:0x353b10 @text="", @name="X">
irb(main):029:0> x.add_to_text("It works!")
=> "It works!"
irb(main):030:0> x.text
=> "It works!"
irb(main):031:0> y = Y.from_x(x)
=> #<Y:0x32cce0 @arr=[], @text="It works!", @name="Y">
irb(main):032:0> y.text
=> "It works!"

There ya go! =)

I hope this helps,

James H.

PS: The only thing some of the more experience people might suggest is
that you consider giving your variable names a more English-like
naming. For example, "l_rslt" into "result", or "p_X" into "source_x".
Ruby is very English-like in syntax, why not keep with the trend? It
makes it easier to read your code, and faster to understand what's
going on after you leave it for a while.

Shea Martin

4/13/2006 6:52:00 PM

0

James Herdman wrote:

> result.text(). Try removing the private condition, and I think you'll

I know my questions was not articulated that well. But that is my
problem, I don't want to make it a public member. In most languages
making a member public means that subclasses can access that member,
even in static/class member methods. I had hoped that this would be the
case in ruby too. But it appears that in ruby, static member methods
are treated the same as non-member methods.

>
> PS: The only thing some of the more experience people might suggest is
> that you consider giving your variable names a more English-like
> naming. For example, "l_rslt" into "result", or "p_X" into "source_x".
> Ruby is very English-like in syntax, why not keep with the trend? It
> makes it easier to read your code, and faster to understand what's going
> on after you leave it for a while.
>


yeah, in order to condense my code for posting purposes I quickly
rewrote it. generally I do use quite descriptive names.

~S

James Herdman

4/15/2006 4:52:00 PM

0

On 2006-04-13 14:52:05 -0400, Shea Martin <null@void.0> said:

> James Herdman wrote:
>
>> result.text(). Try removing the private condition, and I think you'll
>
> I know my questions was not articulated that well. But that is my
> problem, I don't want to make it a public member. In most languages
> making a member public means that subclasses can access that member,
> even in static/class member methods. I had hoped that this would be
> the case in ruby too. But it appears that in ruby, static member
> methods are treated the same as non-member methods.

Perhaps if you went about moving the information in a different way?

e.g.
> x = X.new
> x.add_to_text("Hello!")
> y = Y.new(x.text)
> y.text
"Hello!"

I'm pretty sure you're right about how class methods and private
methods are treated. I tinkered around trying to get it to work as a
protected method, but I couldn't get that as well.

Best of luck,

James H