![]() |
proper use of .java files (layout)
I'm trying to figure out the best way to layout a java program. Should I put each object into its own .java file? If I'm making a card game, that would be 52 .java files. Is that crazy? Normal?
Or should I separate them by suit and just have 4 .java files? Or by value so there are 13 .java files? Thanks! I3D |
Re: proper use of .java files (layout)
On 16.12.2012 16:38, infinitum3d@hotmail.com wrote:
> I'm trying to figure out the best way to layout a java program. > Should I put each object into its own .java file? If I'm making a > card game, that would be 52 .java files. Is that crazy? Normal? Crazy. > Or should I separate them by suit and just have 4 .java files? Or by > value so there are 13 .java files? You better had just one class for Card which has different properties. Which properties you need depends of course on the card at hand and on the application. Sometimes it may make sense to make Card an interface and have different implementing classes. But that all depends on the application that is being written. Kind regards robert -- remember.guy do |as, often| as.you_can - without end http://blog.rubybestpractices.com/ |
Re: proper use of .java files (layout)
On 12/16/2012 10:38 AM, infinitum3d@hotmail.com wrote:
> I'm trying to figure out the best way to layout a java program. > Should I put each object into its own .java file? If I'm making a > card game, that would be 52 .java files. Is that crazy? Normal? > > Or should I separate them by suit and just have 4 .java files? Or by > value so there are 13 .java files? You need to distinguish between classes and objects. You will have one class per Java file (actually you can have more than one, but let us keep this simple to start with). When the program runs then you can create one or more instances of that class - those instances are objects. A deck of card will usually be considered 52 instances/objects of 1 class. Arne |
Re: proper use of .java files (layout)
On 12/16/2012 7:38 AM, infinitum3d@hotmail.com wrote:
> I'm trying to figure out the best way to layout a java program. > Should I put each object into its own .java file? If I'm making a > card game, that would be 52 .java files. Is that crazy? Normal? What Arne and Robert said. In this case you want a single class with two fields, one for suit and one for face value. (You could encode both the suit and the value in to a single field. However this sort of space saving is usually counter-productive, unless you're absolutely sure it's needed.) public class PlayingCard { private final int value; // Ace = 1 private final Suit suit; public static enum Suit { HEARTS, CLUBS, SPADES, DIAMONDS } ... ect.... } You will of course have to make 52 instances of that class. Do that at runtime, don't try to make 52 files. |
Re: proper use of .java files (layout)
Brilliant! That makes perfect sense.
Thank you all for the advice. This will really make things easier for me. -I3D |
Re: proper use of .java files (layout)
In article <50cdede4$0$291$14726298@news.sunsite.dk>,
Arne Vajhøj <arne@vajhoej.dk> wrote: > On 12/16/2012 10:38 AM, infinitum3d@hotmail.com wrote: > > I'm trying to figure out the best way to layout a java program. > > Should I put each object into its own .java file? If I'm making a > > card game, that would be 52 .java files. Is that crazy? Normal? > > > > Or should I separate them by suit and just have 4 .java files? Or > > by value so there are 13 .java files? > > You need to distinguish between classes and objects. > > You will have one class per Java file (actually you can have more > than one, but let us keep this simple to start with). > > When the program runs then you can create one or more instances of > that class - those instances are objects. > > A deck of card will usually be considered 52 instances/objects of 1 > class. infinitum3d: There's a nice example that illustrates this using typesafe enums, introduced in Java 1.5: <http://docs.oracle.com/javase/1.5.0/docs/guide/language/enums.html> -- John B. Matthews trashgod at gmail dot com <http://sites.google.com/site/drjohnbmatthews> |
Re: proper use of .java files (layout)
Thank you John. I'll look into it :)
I3D |
Re: proper use of .java files (layout)
markspace wrote:
> public class PlayingCard { > > private final int value; // Ace = 1 I would make this an enum. "Ace = 1" is not a valid association in the problem domain, and its use as a representation creates risk of an artificial equivalency. > private final Suit suit; That's more like it. > public static enum Suit { HEARTS, CLUBS, SPADES, DIAMONDS } > ... ect.... [sic] > } > > You will of course have to make 52 instances of that class. Do that at No "of course" about it. http://www.hoylegaming.com/rules/sho...spx?RuleID=209 > runtime, don't try to make 52 files. How many cards in a blackjack shoe? http://en.wikipedia.org/wiki/Blackjack If you hard-code certain assumptions, e.g., that there are 52 cards in the deck, your program will be unable to model many games. -- Lew |
Re: proper use of .java files (layout)
On 12/17/2012 10:28 AM, Lew wrote:
> markspace wrote: >> public class PlayingCard { >> >> private final int value; // Ace = 1 > > I would make this an enum. > > "Ace = 1" is not a valid association in the problem domain, and its use > as a representation creates risk of an artificial equivalency. I was actually thinking about that. I don't like the idea of trying to encode most of the values of a face card as enums. Something like this might be a reasonable compromise. public static enum Cards {ACE, DEUCE, KING, QUEEN, JACK } public void set( Cards card, Suit suit ) { switch( card ) { case ACE: value = 1; break; case DEUCE: value = 2; break; case KING: value = 13; break; case QUEEN: value = 12; break; case JACK: value = 11; break; } this.suit = suit; } public void set( int card, Suit suit ) { value = card; this.suit = suit; } I also think it might be valuable to have one implementation of PlayingCard with one internal encoding, then assigning different semantics (e.g., ace high or low) in a separate game object. Trying to overload PlayingCard too much with too much business logic seems to violate encapsulation. A simple wrapper class could easily switch the value of an ace; so could a custom comparator. Without more requirements from the OP, it's really hard to guess what of the many possible solutions is best. So I went with a simple implementation of "ace" (ace = 1) and I'm leaving to other logic to decide how to treat that. You could have other more complicated implementations of PlayingCard, but too much gets too baroque quickly, imo, especially if you don't need all that functionality for most use cases. Another example: in many standard decks, the names of the suits are not Spades, Hearts, etc. but vary by country. Again I'm leaving that for some other part of the program. Localization of card names can be done by wrapping this PlayingCard with a GermanPlayingCard, for example. |
Re: proper use of .java files (layout)
markspace wrote:
> Lew wrote: >> markspace wrote: >>> public class PlayingCard { >>> private final int value; // Ace = 1 > >> I would make this an enum. >> > >> "Ace = 1" is not a valid association in the problem domain, and its use >> as a representation creates risk of an artificial equivalency. > I was actually thinking about that. I don't like the idea of trying to > encode most of the values of a face card as enums. Something like this > might be a reasonable compromise. I wouldn't code *any* of the values of the face cards or the pip cards as anything in the PlayingCard type. > public static enum Cards {ACE, DEUCE, KING, QUEEN, JACK , TEN, NINE, EIGHT, SEVEN, SIX, FIVE, FOUR, TREY, JOKER, > } And I'd put them in order {JOKER, ACE, DEUCE, ..., } > public void set( Cards card, Suit suit ) { 'Card', not 'Cards'. > switch( card ) { > > case ACE: value = 1; break; That's clumsy. But how will this work for Blackjack? > case DEUCE: value = 2; break; > case KING: value = 13; break; > case QUEEN: value = 12; break; > case JACK: value = 11; break; > } > this.suit = suit; > } > > public void set( int card, Suit suit ) { > value = card; Should not be an 'int', I reiterate. There is nothing "integery" about the card name. > this.suit = suit; > } > > I also think it might be valuable to have one implementation of > PlayingCard with one internal encoding, then assigning different Yes, the "internal encoding" is the enum constant. > semantics (e.g., ace high or low) in a separate game object. Trying to That. > overload PlayingCard too much with too much business logic seems to Agreed. > violate encapsulation. A simple wrapper class could easily switch the Not "switch", assign, and not a "simple wrapper class" but a games rule engine. > value of an ace; so could a custom comparator. Without more > requirements from the OP, it's really hard to guess what of the many > possible solutions is best. I was going for modeling a playing card so it would work in any card game. > So I went with a simple but feckless > implementation of "ace" (ace = 1) and I'm > leaving to other logic to decide how to treat that. You could have > other more complicated implementations of PlayingCard, but too much gets You've already included too much by having an 'int' value. > too baroque quickly ^H^H^H^H^H^H^Halready > , imo, especially if you don't need all that > functionality for most use cases. You don't need the 'int' value for any use cases. > Another example: in many standard decks, the names of the suits are not > Spades, Hearts, etc. but vary by country. Again I'm leaving that for Silliness. We know from the OP's problem statement that they intend the French suits. > some other part of the program. Localization of card names can be done > by wrapping this PlayingCard with a GermanPlayingCard, for example. Wrap, wrap, wrap. You sure are addicted to wrapping. I wouldn't recommend that. How would a 'GermanPlayingCard' delegate to the standard French model? I'd use a different type that implements a suitable interface, or just use a different enum. But I can't really see the refactoring clearly from here. I'd need a candidate implementation to refactor. -- Lew |
| All times are GMT. The time now is 04:53 PM. |
Powered by vBulletin®. Copyright ©2000 - 2013, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.