• Post Reply Bookmark Topic Watch Topic
  • New Topic

Array with objects and polymorphism  RSS feed

 
Keith Earl
Greenhorn
Posts: 15
Android Eclipse IDE Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I'm studying about polymorphism right now and decided to do some practicing, but I'm a bit stuck with something.

I have a program I want to make (text based, no gui). There is the main class, an Employee class (sort of a template), a CrewMember class, and a Manager class.

I'll put the code for each class an explain the problem I have.









Mind you, some of the code is a bit incomplete simply because I ran into the problem. As you can see I made an array in the Start class and it holds objects of Employee type, but create a new instance of either a crew member or a manager, sets their wages, hours, and bonus if applicable. I know if I create an array of a certain type, I can't call upon the subclass' method (Manager in this case) because it has a new method that I added. What I'm trying to do is pretty much call upon the getSalary() method in the Manager class/object, but of course I can't. What way would i be able to do that? I tried looking for some answers before coming here and saw people with slightly similar problems, but I read about making the superclass abstract and implementing it into the subclasses. Would that be an option?
 
Henry Wong
author
Sheriff
Posts: 23295
125
C++ Chrome Eclipse IDE Firefox Browser Java jQuery Linux VI Editor Windows
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Keith Earl wrote:
Mind you, some of the code is a bit incomplete simply because I ran into the problem. As you can see I made an array in the Start class and it holds objects of Employee type, but create a new instance of either a crew member or a manager, sets their wages, hours, and bonus if applicable. I know if I create an array of a certain type, I can't call upon the subclass' method (Manager in this case) because it has a new method that I added. What I'm trying to do is pretty much call upon the getSalary() method in the Manager class/object, but of course I can't. What way would i be able to do that? I tried looking for some answers before coming here and saw people with slightly similar problems, but I read about making the superclass abstract and implementing it into the subclasses. Would that be an option?


One easy option ... Confirm that the object (referred by the Employee reference) is indeed a Manager object via the instanceof operator. And if so, cast the Employee to Manager and call the method.

Henry
 
Keith Earl
Greenhorn
Posts: 15
Android Eclipse IDE Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Henry Wong wrote:
Keith Earl wrote:
Mind you, some of the code is a bit incomplete simply because I ran into the problem. As you can see I made an array in the Start class and it holds objects of Employee type, but create a new instance of either a crew member or a manager, sets their wages, hours, and bonus if applicable. I know if I create an array of a certain type, I can't call upon the subclass' method (Manager in this case) because it has a new method that I added. What I'm trying to do is pretty much call upon the getSalary() method in the Manager class/object, but of course I can't. What way would i be able to do that? I tried looking for some answers before coming here and saw people with slightly similar problems, but I read about making the superclass abstract and implementing it into the subclasses. Would that be an option?


One easy option ... Confirm that the object (referred by the Employee reference) is indeed a Manager object via the instanceof operator. And if so, cast the Employee to Manager and call the method.

Henry


Awesome, that seemed to work. I just went ahead and cast employee to manager and was able to call the methods I needed to from the subclass. Thank you very much
 
Campbell Ritchie
Marshal
Posts: 56584
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Alternative suggestion:

Add the method in the Employee class and make it do nothing (or return 0).
 
Keith Earl
Greenhorn
Posts: 15
Android Eclipse IDE Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Campbell Ritchie wrote:Alternative suggestion:

Add the method in the Employee class and make it do nothing (or return 0).


I was thinking about that, but that wasn't the "route" I wanted to go. Since I'm just studying I was trying to figure out different ways to accomplish it and what you suggested I had already thought of, and it's by no means a bad idea, but again I was just seeing if maybe there were other ways. That's mainly because the way I did it now adds more of the polymorphism to it, at least it seemed that way to me. But thank you for the suggestion
 
Winston Gutkowski
Bartender
Posts: 10575
66
Eclipse IDE Hibernate Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Keith Earl wrote:I was thinking about that, but that wasn't the "route" I wanted to go...

Why? To be honest, Henry's idea (and I know very well that he's a fine and knowledgeable fellow) strikes me as the antithesis of polymorphism. Campbell's seems much more "polymorphic" to me - although I'm not sure about the "returning 0" bit.

The whole point of polymorphism is to avoid "dispatch" code - which is precisely what any "if" stack that involves type-checking is. An object's "behaviour" is determined solely by the methods you call on it, and what they do; even if it's nothing.

HIH

Winston
 
Piet Souris
Master Rancher
Posts: 2044
75
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Winston Gutkowski wrote:
Keith Earl wrote:I was thinking about that, but that wasn't the "route" I wanted to go...

Why? To be honest, Henry's idea (and I know very well that he's a fine and knowledgeable fellow) strikes me as the antithesis of polymorphism. Campbell's seems much more "polymorphic" to me - although I'm not sure about the "returning 0" bit.

The whole point of polymorphism is to avoid "dispatch" code - which is precisely what any "if" stack that involves type-checking is. An object's "behaviour" is determined solely by the methods you call on it, and what they do; even if it's nothing.

HIH

Winston

And I agree with Henry. What you describe boils down to that every Employee should have the same methods,
albeit it with different outcomes (i.e. @Overriding).
But the whole point is that you create many "Employee"s by giving each form its own methods, or overriding
existing ones.. And using the 'instanceof'operator is a legal way of finding out what kind of employee you're
dealing with.

Admittedly, 'instanceof' is not very mice, but I bet that the next Java will have a more powerfull
pattern matching.

Greetz,
Piet

 
Keith Earl
Greenhorn
Posts: 15
Android Eclipse IDE Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I think I was misunderstood (or at least didn't word my previous post correctly). Both the ideas suggest I thought were good, I was just simply wondering if there's other ways to go about achieving the same result, may it be through henry's suggestion or campbell's. Ultimately I did go with henry's, and it may be "wrong" because from my understanding casting the manager as an employee would defeat the purpose of the manager class and i could've simply added the bonus methods within the "crewmember" class and achieved what I wanted, right?
 
Piet Souris
Master Rancher
Posts: 2044
75
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Yes and no.

Yes, if you don't want casting, then define everything that you can in the 'Employee'
class. But then the big question is: how do you discriminate between all kinds of
employee?

That is why you would desing a minimal, even abstract, class 'Employee', and you
discriminate between all possible types by creating a subclass for each type.

The advantage is that when you create yet another type of Employee, then you can
do that without any need to change the original 'Employee' class.

And it is quite natural, when dealing with an Employee, that you ask 'what kind
of Employee are you?

But this all is not some hard law. If you do not like this approach, then go for
another approach, like the one that Campbell suggests, or whatever you
can come up with.

Greetz,
Piet
 
Winston Gutkowski
Bartender
Posts: 10575
66
Eclipse IDE Hibernate Ubuntu
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Keith Earl wrote:I think I was misunderstood (or at least didn't word my previous post correctly). Both the ideas suggest I thought were good, I was just simply wondering if there's other ways to go about achieving the same result, may it be through henry's suggestion or campbell's. Ultimately I did go with henry's, and it may be "wrong" because from my understanding casting the manager as an employee would defeat the purpose of the manager class and i could've simply added the bonus methods within the "crewmember" class and achieved what I wanted, right?

Actually, I think it has more to do with "objectivity".

Henry's idea will certainly solve the problem, but it's a "procedural" approach - ie, you're solving it with code - when my assumption was that you wanted to understand polymorphism better.

I also think that you have more than one problem here:

1. You've defined "total pay" as 'wage * hours', when in fact, for a Manager, that's not their total pay, because s/he might also have a bonus.
2. You've created a separate method in your Manager class (getSalary()) to return the equivalent of what getTotalPay() returns for all other Employees.

Here's my suggestion:

1. Instead of a getSalary() method, have a baseSalary() method instead, and have that return 'wage * hours', Indeed, you could simply implement it as:
return super.getTotalPay();
because that's precisely what Employee.getTotalPay() does.

2. Override getTotalPay() in your Manager class, and have it return 'baseSalary() + bonus'.

Now you'll have a method (getTotalPay()) that behaves differently for different subtypes, and you won't have to write any "type-checking" code to demonstrate it - and that's what polymorphism is all about.

HIH

Winston
 
Winston Gutkowski
Bartender
Posts: 10575
66
Eclipse IDE Hibernate Ubuntu
  • Likes 1
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Keith Earl wrote:Ultimately I did go with henry's, and it may be "wrong"...

I don't think there's any "right" or "wrong" here, but consider this:

Suppose you added two new subtypes: Director and SalesPerson.

Directors get share options as part of their pay (or "salary"); and sales people get bonuses based on sales quotas.
What do you do now? Have three "if" statements for checking type?

This is precisely the sort of thing that polymorphism is designed to avoid. Instead of checking types, you define a method that is implemented differently for each subtype - usually by overriding.

Now personally, I'd say that's getTotalPay(); but they're your classes, so you need to decide what seems most natural to you.

Again, HIH.

Winston
 
Campbell Ritchie
Marshal
Posts: 56584
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Actually, I was feeling a bit timid yesterday. Maybe I should have said create an Employee interface. The old sort of interface before they invented default methods.
 
Keith Earl
Greenhorn
Posts: 15
Android Eclipse IDE Java
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Yes I can try these suggestions. Thank you
 
Winston Gutkowski
Bartender
Posts: 10575
66
Eclipse IDE Hibernate Ubuntu
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Keith Earl wrote:Yes I can try these suggestions. Thank you

You're most welcome.

Winston
 
Campbell Ritchie
Marshal
Posts: 56584
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Winston Gutkowski wrote: . . .
You're most welcome.

Winston
Same here
 
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!