views:

728

answers:

3

I am writing a little game in which the user is asked for their race and class. There are five possible races of string[5] and four possible classes of string[9].

How do I program pascal to 1. define the five races and four classes as constants, 2. check the user input to see whether the input is within the possible races and classes - without using multiple IF statements?

Any hints will be appreciated.

+2  A: 

Since your input is strictly defined, my first question is, must you use strings as the user input? Can you not give the user a choice? Say a drop down? Then you can map each choice to an enumeration.

type
  race = (rcRace0, rcRace1, rcRace2 rcRace3, rcRace4);


case race(Input) of  //input is an integer, index of the drop down list for example
  rcRace0 : //perform processing for race 0
  rcRace1 : //perform processing for race 1
  rcRace2 : //perform processing for race 2
  rcRace3 : //perform processing for race 3
  rcRace4 : //perform processing for race 4
end;

Same for class.

Steve
Thanks Steve. It's a good, tidy solution.
A: 

I find you should follow Steves solution. But if using strings is your way, you could use a TStringList (in Delphi/possibly FreePascal). You could fill it with your races and then evaluate the players answer using the IndexOf function of the TStringList. It returns the index of the passed string or -1 when the passed string isn't in the List.

Anyway i'd strongly recommend Steves solution :)

BloodySmartie
He might not have to code it himself, but under the hood, IndexOf does exactly what the OP wanted to avoid doing.
Mason Wheeler
+2  A: 

I would recommend Steves solution as the starting point, but go a bit further with the use of enumerated types and sets...

type
    TRace = (rcRace0, rcRace1, rcRace2, rcRace3, rcRace4);

    TCharacterClass = (ccClass0, ccClass1, ccClass2, ccClass3);

    TCharacterClassSet = set of TCharacterClass;

const
    validCombinations : array[TRace] of TCharacterClassSet = (
        [ccClass0, ccClass1, ccClass2, ccClass3],  // race0 can be any class
        [ccClass0, ccClass2],                      // race1 
        [ccClass0, ccClass1, ccClass2],            // race2
        [ccClass0, ccClass3],                      // race3
        [ccClass0]                                 // race4
        );

You could also set up constants for the race names and character classes:

const
    raceNames : array[TRace] of string = (
        'Race 0',
        'Race 1',
        'Race 2',
        'Race 3',
        'Race 4'
        );

    characterClassNames = array[TCharacterClass] of string = (
        'Class 0',
        'Class 1 ',
        'Class 2',
        'Class 3'
        );

Now, if you use comboboxes for user input and map the input to these enumerated types, the check if a combination is valid is simple:

function ValidRaceAndClass( aRace : TRace; aClass : TCharacterClass ) : Boolean;
    begin
    result := aClass in validCombinations[ aRace ];
    end;
Alistair Ward
I agree with this answer. Your data is basically enums not strings. You do not have "five possible races of string[5]". You have "five possible races". Which can be displayed as string[5]. But store then as enums.
Anthony