Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > Java > One object passing members to another class, modifying values

Reply
Thread Tools

One object passing members to another class, modifying values

 
 
craigslist.jg@gmail.com
Guest
Posts: n/a
 
      05-10-2007
Hi,

Let's say I have an instance of ClassA, which has an instance variable
holding a list of numbers as an array (for simplicity's sake). Let's
call this instance variable, arrayA. Let's assume all instVars are
public.

Now, ClassB needs to have access to arrayA, and delete some members
within the array.

Based on OOP principles, what's the better / cleaner implementation
for this?

1. Create a couple of instVars in ClassB:
instVar1 : reference to ArrayA
instVar2: new array keeping track of deleted members

Within ClassA, instantiate ClassB, and set instVar1.
When ClassB is done, within ClassA, delete members from arrayA based
on instVar2.

ClassA doStuff()

classB = new ClassB
classB.instVar1 = arrayA
classB.compileRemovedItems()
arrayA.removeAll(classB.instVar2)

ClassB compileRemovedItems()

instVar2 = setRemovedItems()

2. As in (1), create a couple of instVars, but instantiate the
instVar1 within classB

ClassA doStuff()

classB = new ClassB
classB.compileRemovedItems()
arrayA.removeAll(classB.instVar2)

ClassB compileRemovedItems()

instVar1 = classA.arrayA
instVar2 = setRemovedItems()

3. From ClassB, access arrayA directly, and remove the items there.

ClassA doStuff()

classB = new ClassB
classB.compileRemovedItems()

ClassB compileRemovedItems()
instVar1 = classA.arrayA
instVar2 = setRemovedItems()
instVar1.removeAll(instVar2)


With 1, classB has no dependencies on classA, but I have to keep on
setting instVar1 at every point I need to call compileRemovedItems.

With 2, classB sets instVar1 from classA so I save that extra step.

3 is even more dependent on classA, as it is accessing and modifying
arrayA directly.


Thanks for reading.

 
Reply With Quote
 
 
 
 
Z.
Guest
Posts: n/a
 
      05-10-2007
wrote:
> Let's say I have an instance of ClassA, which has an instance variable
> holding a list of numbers as an array (for simplicity's sake). Let's
> call this instance variable, arrayA. Let's assume all instVars are
> public.
>
> Now, ClassB needs to have access to arrayA, and delete some members
> within the array.
>
> Based on OOP principles, what's the better / cleaner implementation
> for this?


The proper way is for ClassB to access (read/write/delete) ClassA's
fields only through public accessor methods of ClassA.

ClassA should not expose modifiable fields directly and ClassB should
not keep local copies of ClassA's fields in ClassB.

 
Reply With Quote
 
 
 
 
H. S. Lahman
Guest
Posts: n/a
 
      05-10-2007
Responding to Craigslist.jg...

> Let's say I have an instance of ClassA, which has an instance variable
> holding a list of numbers as an array (for simplicity's sake). Let's
> call this instance variable, arrayA. Let's assume all instVars are
> public.


So arrayA is a collection class implementing the R1 relationship in

1 R1 *
[ClassA] --------------- [Number]

> Now, ClassB needs to have access to arrayA, and delete some members
> within the array.


If ClassB needs access to those same numbers, they can't be part of the
ClassA implementation as a fundamental language data structure like an
array. That's because anything in the ClassA implementation needs to be
hidden from the outside world, so it would be invisible to ClassB. So
you really have, at the OOA/D level:

[CLassA]
| 1
|
| R1
|
| *
[Number]
| *
|
| R2
|
| 1
[ClassB]

OTOH, making a number a first class object is a bit of overkill. So what
one really wants is a bit more abstraction:

[ClassA]
| 1
|
| R1
|
| 1
[NumberList]
+ getNumber(entryID) // e.g., whatever
+ setNumber(entryID, value) // e.g., whatever
| 1
|
| R2
|
| 1
[ClassB]

Now [NumberList] is a reasonable first class object abstraction to which
both [ClassA] and [ClassB] have references and those references
instantiate the R1 and R2 relationships, respectively.

Note that all this does is take arrayA out of the [ClassA]
implementation and make it a peer class of both ClassA and ClassB. The
only trickiness lies in referential integrity (i.e., instantiating the
relationships as [ClassA] and [ClassB] objects are created). That
mechanics will depend upon the specific problem in hand, but a "factory"
objects can encapsulate those sorts of rules.


*************
There is nothing wrong with me that could
not be cured by a capful of Drano.

H. S. Lahman

Pathfinder Solutions
http://www.pathfindermda.com
blog: http://pathfinderpeople.blogs.com/hslahman
"Model-Based Translation: The Next Step in Agile Development". Email
for your copy.
Pathfinder is hiring:
http://www.pathfindermda.com/about_us/careers_pos3.php.
(88OOA-PATH



 
Reply With Quote
 
Daniel T.
Guest
Posts: n/a
 
      05-11-2007
wrote:

> Let's say I have an instance of ClassA, which has an instance variable
> holding a list of numbers as an array (for simplicity's sake). Let's
> call this instance variable, arrayA. Let's assume all instVars are
> public.


First mistake. Why make such an assumption?

> Now, ClassB needs to have access to arrayA, and delete some members
> within the array.


A particular object of ClassB, or the class itself? Are the members that
ClassB deletes supposed to also be deleted in the list that the ClassA
object has?

> Based on OOP principles, what's the better / cleaner implementation
> for this?


If ClassB is not a peer to ClassA then I would likely have the ClassA
object pass a reference to the array when it creates the ClassB object.
Then let the ClassB object delete the numbers itself. This way, ClassB
is in no way dependent on ClassA and can be used by any class that is
willing and able to pass ClassB an array of numbers.

The above can tend to obfuscate the code though. A better choice would
be to have a ClassA object instantiate a ClassB object, and have the
ClassB object manage the array of numbers.

[ClassA]--->[ClassB]--->[ArrayA]

Instead of:

[ClassA]----->[ClassB]
| |
| |
+->[ArrayA]<-+
 
Reply With Quote
 
squirrel
Guest
Posts: n/a
 
      05-11-2007
On May 10, 11:42 pm, craigslist...@gmail.com wrote:
> Hi,
>
> Let's say I have an instance of ClassA, which has an instance variable
> holding a list of numbers as an array (for simplicity's sake). Let's
> call this instance variable, arrayA. Let's assume all instVars are
> public.
>
> Now, ClassB needs to have access to arrayA, and delete some members
> within the array.
>
> Based on OOP principles, what's the better / cleaner implementation
> for this?
>
> 1. Create a couple of instVars in ClassB:
> instVar1 : reference to ArrayA
> instVar2: new array keeping track of deleted members
>
> Within ClassA, instantiate ClassB, and set instVar1.
> When ClassB is done, within ClassA, delete members from arrayA based
> on instVar2.
>
> ClassA doStuff()
>
> classB = new ClassB
> classB.instVar1 = arrayA
> classB.compileRemovedItems()
> arrayA.removeAll(classB.instVar2)
>
> ClassB compileRemovedItems()
>
> instVar2 = setRemovedItems()
>
> 2. As in (1), create a couple of instVars, but instantiate the
> instVar1 within classB
>
> ClassA doStuff()
>
> classB = new ClassB
> classB.compileRemovedItems()
> arrayA.removeAll(classB.instVar2)
>
> ClassB compileRemovedItems()
>
> instVar1 = classA.arrayA
> instVar2 = setRemovedItems()
>
> 3. From ClassB, access arrayA directly, and remove the items there.
>
> ClassA doStuff()
>
> classB = new ClassB
> classB.compileRemovedItems()
>
> ClassB compileRemovedItems()
> instVar1 = classA.arrayA
> instVar2 = setRemovedItems()
> instVar1.removeAll(instVar2)
>
> With 1, classB has no dependencies on classA, but I have to keep on
> setting instVar1 at every point I need to call compileRemovedItems.
>
> With 2, classB sets instVar1 from classA so I save that extra step.
>
> 3 is even more dependent on classA, as it is accessing and modifying
> arrayA directly.
>
> Thanks for reading.


If you just want to decouple the dependency of classA and classB, why
not apply Vistor pattern.

 
Reply With Quote
 
Daniel T.
Guest
Posts: n/a
 
      05-12-2007
squirrel <> wrote:

> If you just want to decouple the dependency of classA and classB, why
> not apply Vistor pattern.


I think that would be a little extreme in this case. Simply removing the
back-pointer would be enough to do the job.
 
Reply With Quote
 
AndyW
Guest
Posts: n/a
 
      05-12-2007
On 10 May 2007 08:42:58 -0700, wrote:

>Hi,
>
>Let's say I have an instance of ClassA, which has an instance variable
>holding a list of numbers as an array (for simplicity's sake). Let's
>call this instance variable, arrayA. Let's assume all instVars are
>public.
>
>Now, ClassB needs to have access to arrayA, and delete some members
>within the array.
>
>Based on OOP principles, what's the better / cleaner implementation
>for this?


I use an OO rule that states "An object should not modify the contents
of another object, but should request that the other object modify
itself".

Its based on the principle of encapsulation.

One can use 'loose coupling' by using an event mechanism or 'tight
coupling' by calling a function call defined in the classes public
interface.


----------------
AndyW,
Mercenary Software Developer
 
Reply With Quote
 
Robin Barendregt
Guest
Posts: n/a
 
      05-12-2007
Same here.
And preferably use meaningful names when possible, such as addCustomer:,
removeCustomer: instead of just add:, remove:

"AndyW" <> schreef in bericht
news:...
> On 10 May 2007 08:42:58 -0700, wrote:
>
>>Hi,
>>
>>Let's say I have an instance of ClassA, which has an instance variable
>>holding a list of numbers as an array (for simplicity's sake). Let's
>>call this instance variable, arrayA. Let's assume all instVars are
>>public.
>>
>>Now, ClassB needs to have access to arrayA, and delete some members
>>within the array.
>>
>>Based on OOP principles, what's the better / cleaner implementation
>>for this?

>
> I use an OO rule that states "An object should not modify the contents
> of another object, but should request that the other object modify
> itself".
>
> Its based on the principle of encapsulation.
>
> One can use 'loose coupling' by using an event mechanism or 'tight
> coupling' by calling a function call defined in the classes public
> interface.
>
>
> ----------------
> AndyW,
> Mercenary Software Developer



 
Reply With Quote
 
RichardETVS
Guest
Posts: n/a
 
      05-15-2007
While encapsulation is a general rule, and a good one, there can be
case where it is not the best, in my humble opinion.

Take an object database like db4o, by example (www.dbf4.com ) . You
save an object with something like
"anObjectDataBaseManager.Save(TheObjectIwantToSave ). And it is saved,
even its private fields. To fully load an object, you can use a syntax
like "ObjectContainer.Activate(TheObjectIwantToFullyLoa d,
int.MaxValue)".

So, in those cases, the encapsulation is broken. For a data layer, I
had to something like that. The BO objects ask to the data layer to
save and update them. I did not want to use .net reflection, so I used
the Separate Interface Pattern, and with an explicit interface, my BO
expose all their private fields to the data layer.

I have to amit my solution has a problem. The user interface layer, in
C#, asks a reference to the interface module, it seems that in VB it
is not the case. So, if a developer really want it, he can use the
explicit interface mechanism to acces private BO fields.



Richard

 
Reply With Quote
 
Ed
Guest
Posts: n/a
 
      05-16-2007
On 15 Maj, 11:51, RichardETVS <PETI...@e-i.com> wrote:
> While encapsulation is a general rule, and a good one, there can be
> case where it is not the best, in my humble opinion.
>
> Take an object database like db4o, by example (www.dbf4.com) . You
> save an object with something like
> "anObjectDataBaseManager.Save(TheObjectIwantToSave ). And it is saved,
> even its private fields. To fully load an object, you can use a syntax
> like "ObjectContainer.Activate(TheObjectIwantToFullyLoa d,
> int.MaxValue)".
>
> So, in those cases, the encapsulation is broken. For a data layer, I
> had to something like that. The BO objects ask to the data layer to
> save and update them. I did not want to use .net reflection, so I used
> the Separate Interface Pattern, and with an explicit interface, my BO
> expose all their private fields to the data layer.
>
> I have to amit my solution has a problem. The user interface layer, in
> C#, asks a reference to the interface module, it seems that in VB it
> is not the case. So, if a developer really want it, he can use the
> explicit interface mechanism to acces private BO fields.
>
> Richard


Hej, Richard,

While I fully agree that there is always a case for breaking a rule in
special circumstances (even encapsulation), could I just note a humble
alternative to your approach, though I lack your insight into the
problem?

Firstly, encapsulation can help insulate a class from changes in
another class.

In the solution you have above, I presume that the following line
means: create an instance of TheObjectIwantToFullyLoad and set its
MaxValue accordingly:
"ObjectContainer.Activate(TheObjectIwantToFullyLoa d, int.MaxValue)"

If this is the case, then we can consider what happens when
TheObjectIwantToFullyLoad gets a new field variable, let's call it:
String name.

Now, both TheObjectIwantToFullyLoad must change (to add this new
variable) and - more importantly - ObjectContainer must change, as it
must now call:
"ObjectContainer.Activate(TheObjectIwantToFullyLoa d, int.MaxValue,
string.name)"

This, we note, is the price of breaking encapsulation.

The question is: could there be a way to respect encapsulation so
that
ObjectContainer isn't affected by any changes to the internals of
TheObjectIwantToFullyLoad?

An answer could be to have TheObjectIwantToFullyLoad (and any
serialisable object) responsible for its own data serialisation. It
could have a method save(BitStream stream). This method is called by
ObjectContainer and it passes in the stream that will be written to
the file system.

It is then up to TheObjectIwantToFullyLoad to convert all its private
data to a bit-stream representation and write this data to the bit-
stream.

The reverse is true when reading a bit-stream from the file system:
TheObjectIwantToFullyLoad itself will be resonsible for inspecting
the bit-stream and converting it back to an int and a string value.

Now, changes to TheObjectIwantToFullyLoad do not affect the
ObjectContainer.

..ed

--
www.EdmundKirwan.com - Home of The Fractal Class Composition.

Download Fractality, free Java code analyzer:
http://www.EdmundKirwan.com/servlet/...c-page130.html

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Passing checkbox values from one JSP page to another udelram@gmail.com Java 4 06-24-2011 09:28 AM
passing values from one web form to another web form bbawa1@yahoo.com ASP .Net 5 06-12-2007 05:50 AM
passing values from one form to another eight02645999@yahoo.com Python 2 11-12-2005 05:31 PM
Error passing values from one pahge to another =?Utf-8?B?Q2hyaXM=?= ASP .Net 8 05-16-2005 07:54 PM
Passing value from one script on one page to another script on another page. Robert Cohen ASP General 3 07-15-2003 01:46 PM



Advertisments
 



1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57