Solve Exercise 13
This commit is contained in:
parent
c99b0817c0
commit
39a1585a4b
3 changed files with 243 additions and 0 deletions
162
app/src/main/java/ch/nuth/zhaw/exbox/BakeryCookieServer.java
Normal file
162
app/src/main/java/ch/nuth/zhaw/exbox/BakeryCookieServer.java
Normal file
|
@ -0,0 +1,162 @@
|
||||||
|
package ch.nuth.zhaw.exbox;
|
||||||
|
|
||||||
|
import java.util.Random;
|
||||||
|
import java.util.stream.Stream;
|
||||||
|
|
||||||
|
public class BakeryCookieServer implements CommandExecutor {
|
||||||
|
private Ingredient mehl, zucker, salz, eier, butter, milch, zitrone, konfituere, schokolade;
|
||||||
|
private Ingredient[] stockOfIngredients;
|
||||||
|
|
||||||
|
private Cookie mailaenderli, spitzbuben, brownies;
|
||||||
|
private Cookie[] cookiesOfBakery;
|
||||||
|
|
||||||
|
private float temperature;
|
||||||
|
private Random heatGenerator = new Random();
|
||||||
|
|
||||||
|
public String execute (String input) {
|
||||||
|
initialiseIngredients();
|
||||||
|
initialiseCookies();
|
||||||
|
return simulatedAnnealing();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* initializes the ingredients and their quantity in stock
|
||||||
|
*/
|
||||||
|
private void initialiseIngredients() {
|
||||||
|
mehl = new Ingredient("Mehl", 20000);
|
||||||
|
zucker = new Ingredient("Zucker", 25000);
|
||||||
|
salz = new Ingredient("Salz", 5000);
|
||||||
|
eier = new Ingredient("Eier", 2000);
|
||||||
|
butter = new Ingredient("Butter", 10000);
|
||||||
|
milch = new Ingredient("Milch", 5000);
|
||||||
|
zitrone = new Ingredient("Zitrone", 10000);
|
||||||
|
konfituere = new Ingredient("Konfitüre", 2000);
|
||||||
|
schokolade = new Ingredient("Schokolade", 1000);
|
||||||
|
stockOfIngredients = new Ingredient[] { mehl, zucker, salz, eier, butter, milch, zitrone, konfituere, schokolade };
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* initialises the cookies and the ingredients used for one cookie
|
||||||
|
*/
|
||||||
|
private void initialiseCookies() {
|
||||||
|
mailaenderli = new Cookie("Mailänderli", 7);
|
||||||
|
mailaenderli.addIngredient(mehl, 15);
|
||||||
|
mailaenderli.addIngredient(zucker, 11.25f);
|
||||||
|
mailaenderli.addIngredient(salz, 0.2f);
|
||||||
|
mailaenderli.addIngredient(eier, 5);
|
||||||
|
mailaenderli.addIngredient(butter, 12.5f);
|
||||||
|
mailaenderli.addIngredient(milch, 1);
|
||||||
|
mailaenderli.addIngredient(zitrone, 7.5f);
|
||||||
|
|
||||||
|
spitzbuben = new Cookie("Spitzbuben", 6);
|
||||||
|
spitzbuben.addIngredient(mehl, 25.5f);
|
||||||
|
spitzbuben.addIngredient(zucker, 6.25f);
|
||||||
|
spitzbuben.addIngredient(salz, 0.15f);
|
||||||
|
spitzbuben.addIngredient(eier, 4);
|
||||||
|
spitzbuben.addIngredient(butter, 12.5f);
|
||||||
|
spitzbuben.addIngredient(konfituere, 10.5f);
|
||||||
|
|
||||||
|
brownies = new Cookie("Schoggibuben", 6);
|
||||||
|
brownies.addIngredient(mehl, 15.5f);
|
||||||
|
brownies.addIngredient(zucker, 10);
|
||||||
|
brownies.addIngredient(salz, 0.10f);
|
||||||
|
brownies.addIngredient(eier, 3);
|
||||||
|
brownies.addIngredient(butter, 10.5f);
|
||||||
|
brownies.addIngredient(schokolade, 20.5f);
|
||||||
|
|
||||||
|
cookiesOfBakery = new Cookie[] {mailaenderli, spitzbuben, brownies};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* uses simulated annealing to generate new possible solutions
|
||||||
|
* @return string contains the best found solution for all cookies
|
||||||
|
*/
|
||||||
|
private String simulatedAnnealing() {
|
||||||
|
String result = "";
|
||||||
|
|
||||||
|
// TODO
|
||||||
|
float startTemperature = temperature;
|
||||||
|
creationOfInitialConfiguration();
|
||||||
|
|
||||||
|
while (temperature >= 0) {
|
||||||
|
generateNextTestConfiguration();
|
||||||
|
|
||||||
|
if (checkIfValidSolution())
|
||||||
|
{
|
||||||
|
if (checkIfMoreCookiesAndBetterSolution() || (Math.random() * startTemperature) > temperature)
|
||||||
|
{
|
||||||
|
for (Cookie cookie : cookiesOfBakery) {
|
||||||
|
cookie.setBestNrOfCookies(cookie.getTestedNrOfCookies());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
temperature -= heatGenerator.nextFloat();
|
||||||
|
}
|
||||||
|
|
||||||
|
for (Cookie cookie : cookiesOfBakery) {
|
||||||
|
result += cookie.getNameOfCookie() + ": " + cookie.getBestNrOfCookies() + ", ";
|
||||||
|
}
|
||||||
|
return result + "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* initialize very first run (temperature)
|
||||||
|
*/
|
||||||
|
private void creationOfInitialConfiguration() {
|
||||||
|
// TODO
|
||||||
|
temperature = 10_000_000;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generate a randomized new test set of cookies
|
||||||
|
*/
|
||||||
|
private void generateNextTestConfiguration() {
|
||||||
|
// TODO
|
||||||
|
|
||||||
|
for (Cookie cookie : cookiesOfBakery)
|
||||||
|
{
|
||||||
|
if (heatGenerator.nextBoolean())
|
||||||
|
{
|
||||||
|
int incremental = cookie.getBestNrOfCookies() > 0 ? (heatGenerator.nextBoolean() ? 1 : -1) : 1;
|
||||||
|
cookie.setTestedNrOfCookies(cookie.getBestNrOfCookies() + incremental);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if this is a better solution (more cookies) then the solution already found
|
||||||
|
* @return true if the newly tested solution is better
|
||||||
|
*/
|
||||||
|
private boolean checkIfMoreCookiesAndBetterSolution() {
|
||||||
|
// TODO
|
||||||
|
return Stream.of(cookiesOfBakery).mapToInt((cookie) -> cookie.getTestedNrOfCookies()).sum()
|
||||||
|
>= Stream.of(cookiesOfBakery).mapToInt((cookie) -> cookie.getBestNrOfCookies()).sum();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if there are enough ingredients to bake this new solution
|
||||||
|
* @return true if enough ingredients
|
||||||
|
*/
|
||||||
|
private boolean checkIfValidSolution() {
|
||||||
|
// TODO
|
||||||
|
for (Ingredient ingredient : stockOfIngredients)
|
||||||
|
{
|
||||||
|
ingredient.initialiseStockBeforeCooking();
|
||||||
|
}
|
||||||
|
|
||||||
|
for (Cookie cookie : cookiesOfBakery)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < cookie.getNrOfIngredients(); i++)
|
||||||
|
{
|
||||||
|
if (!cookie.getIngredientOfCookie(i).removeFromStock(cookie.getGramsPerIngredient(i) * cookie.getTestedNrOfCookies()))
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
56
app/src/main/java/ch/nuth/zhaw/exbox/Cookie.java
Normal file
56
app/src/main/java/ch/nuth/zhaw/exbox/Cookie.java
Normal file
|
@ -0,0 +1,56 @@
|
||||||
|
package ch.nuth.zhaw.exbox;
|
||||||
|
|
||||||
|
public class Cookie {
|
||||||
|
private final String nameOfCookie;
|
||||||
|
private int bestNrOfCookies = 0;
|
||||||
|
private int testedNrOfCookies;
|
||||||
|
private final Ingredient[] ingredientsOfCookie;
|
||||||
|
private final float[] gramsPerIngredient;
|
||||||
|
private int nrOfIngredient = 0;
|
||||||
|
|
||||||
|
Cookie(String nameOfCookie, int nrOfIngridients) {
|
||||||
|
this.nameOfCookie = nameOfCookie;
|
||||||
|
ingredientsOfCookie = new Ingredient[nrOfIngridients];
|
||||||
|
gramsPerIngredient = new float[nrOfIngridients];
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getNameOfCookie() {
|
||||||
|
return nameOfCookie;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getBestNrOfCookies() {
|
||||||
|
return bestNrOfCookies;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setBestNrOfCookies(int bestNrOfCookies) {
|
||||||
|
this.bestNrOfCookies = bestNrOfCookies;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getTestedNrOfCookies() {
|
||||||
|
return testedNrOfCookies;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setTestedNrOfCookies(int testedNrOfCookies) {
|
||||||
|
this.testedNrOfCookies = testedNrOfCookies;
|
||||||
|
}
|
||||||
|
|
||||||
|
void addIngredient(Ingredient ingredient, float gramsPerCookie) {
|
||||||
|
ingredientsOfCookie[nrOfIngredient] = ingredient;
|
||||||
|
this.gramsPerIngredient[nrOfIngredient] = gramsPerCookie;
|
||||||
|
nrOfIngredient++;
|
||||||
|
}
|
||||||
|
|
||||||
|
Ingredient getIngredientOfCookie(int nrOfIngredient)
|
||||||
|
{
|
||||||
|
return ingredientsOfCookie[nrOfIngredient];
|
||||||
|
}
|
||||||
|
|
||||||
|
float getGramsPerIngredient(int nrOfIngredient)
|
||||||
|
{
|
||||||
|
return gramsPerIngredient[nrOfIngredient];
|
||||||
|
}
|
||||||
|
|
||||||
|
int getNrOfIngredients() {
|
||||||
|
return nrOfIngredient;
|
||||||
|
}
|
||||||
|
}
|
25
app/src/main/java/ch/nuth/zhaw/exbox/Ingredient.java
Normal file
25
app/src/main/java/ch/nuth/zhaw/exbox/Ingredient.java
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
package ch.nuth.zhaw.exbox;
|
||||||
|
|
||||||
|
public class Ingredient {
|
||||||
|
private final String name;
|
||||||
|
private final float gramInBakery;
|
||||||
|
private float gramUsedForBaking;
|
||||||
|
|
||||||
|
Ingredient (String name, int gramInBakery) {
|
||||||
|
this.name = name;
|
||||||
|
this.gramInBakery = gramInBakery;
|
||||||
|
}
|
||||||
|
|
||||||
|
void initialiseStockBeforeCooking() {
|
||||||
|
gramUsedForBaking = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean removeFromStock(float gramToRemove) {
|
||||||
|
gramUsedForBaking += gramToRemove;
|
||||||
|
return gramUsedForBaking <= gramInBakery;
|
||||||
|
}
|
||||||
|
|
||||||
|
String getRemainingStock() {
|
||||||
|
return name + ": " + (gramInBakery - gramUsedForBaking) + ", ";
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue