Programming: Hammurabi I - Solution
Solution
The following two source files are a solution to the
Hammurabi I programming problem.
This solution has expanded somewhat on the minimum requirements.
Main program
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
|
// File : oop/Hammurabi1.java
// Purpose: Simulate running a kingdom.
// Author : Fred Swartz
// Date : 2005 May 8
import javax.swing.*;
public class Hammurabi1 {
//=========================================================== main
public static void main(String[] args) {
Kingdom samaria = new Kingdom();
int year = 1;
while (year <= 10 && samaria.getPopulation() > 0) {
displayStatus(samaria, year);
int availableGrain = samaria.getGrain();
//... Get the amount of grain to feed peasants.
String message =
"Exalted Ruler, How much of the " + availableGrain
+ " bushels do you wish to feed the "
+ samaria.getPopulation() + " peasants?";
int food = getInt(message, 0, availableGrain);
//... Take the minimum of the amount of remaining
// grain, and the maximum plantable.
int maxSeed = Math.min(availableGrain-food,
samaria.getMaximumUsableSeed());
//... Get the amount of grain to use for planting.
message = "Exalted Ruler, how much of the plantable "
+ maxSeed + " bushels should be used?";
int seeds = getInt(message, 0, maxSeed);
//... Simulate one year
samaria.simulateOneYear(food, seeds);
year++;
}
JOptionPane.showMessageDialog(null,
"We have survived because of your brillance, "
+ "Most Exhalted Ruler!");
displayStatus(samaria, year);
}
//=============================================================== getInt
// Prompts for an integer in a range.
// Doesn't handle null (CANCEL) or bad input.
private static int getInt(String prompt, int min, int max) {
int result;
do {
String strVal = JOptionPane.showInputDialog(null, prompt);
result = Integer.parseInt(strVal);
if (result < min || result > max) {
JOptionPane.showMessageDialog(null,
"ERROR: Input must be between " + min + " and " + max);
}
} while (result < min || result > max);
return result;
}
//======================================================== displayStatus
private static void displayStatus(Kingdom country, int yr) {
JOptionPane.showMessageDialog(null,
"Exalted Ruler, your riches at year " + yr + ":"
+ "\n Peasants = " + country.getPopulation()
+ "\n Grain = " + country.getGrain());
}
}
|
Kingdom class
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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
|
// File : oop/Kingdom.java
// Purpose: Represents a "kingdom".
// Author : Fred Swartz
// Date : 05 May 2005
class Kingdom {
//============================================================== constants
public static int MIN_GRAIN_TO_SURVIVE = 20;
public static int MAX_LAND_FARMABLE_PER_PERSON = 10;
public static int SEED_REQUIRED_PER_ACRE = 2;
//===================================================== instance variables
private int myPopulation = 100;
private int myGrain = 3000;
private int myArea = 1000;
//========================================================== getPopulation
public int getPopulation() {
return myPopulation;
}
//=============================================================== getGrain
public int getGrain() {
return myGrain;
}
//================================================================ getArea
public int getArea() {
return myArea;
}
//================================================== getAmountOfFoodNeeded
public int getAmountOfFoodNeeded() {
return myPopulation * MIN_GRAIN_TO_SURVIVE;
}
//=================================================== getMaximumUsableSeed
/** Compute the maximum number of bushels of seed that can be used
* based on the number of peasants for farming, and the amount of
* land.
*/
public int getMaximumUsableSeed() {
int peasantFarmableArea = myPopulation * MAX_LAND_FARMABLE_PER_PERSON;
int maxFarmableArea = Math.min(myArea, peasantFarmableArea);
return SEED_REQUIRED_PER_ACRE * maxFarmableArea;
}
//======================================================== simulateOneYear
public void simulateOneYear(int food, int seed) {
//... Don't allow illegal parameter values. These values
// should have been checked before calling this method.
// Bad values should have been corrected in the user interface.
assert food >= 0 && seed >= 0 : "simulateOneYear negative values.";
assert food + seed <= myGrain : "simulateOneYear parameters too large.";
//... Remove the requested amount of grain from storage
myGrain = myGrain - food - seed;
//... Compute the random harvest.
int usableSeed = Math.min(seed, getMaximumUsableSeed());
int acresPlanted = usableSeed / SEED_REQUIRED_PER_ACRE;
int yieldPerAcre = 2 + (int)(5 * Math.random());
int harvest = yieldPerAcre * acresPlanted;
//... Compute the new population
myPopulation = myPopulation * food / getAmountOfFoodNeeded();
//... Add the new havest to the grain in storage.
myGrain += harvest;
}
}
|