Updated Mastermind, Fibonacci.
This commit is contained in:
@@ -36,7 +36,8 @@ class Examples {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// A generic list.
|
// A generic list.
|
||||||
interface ILo<A> {}
|
interface ILo<A> {
|
||||||
|
}
|
||||||
|
|
||||||
class Cons<A> implements ILo<A> {
|
class Cons<A> implements ILo<A> {
|
||||||
|
|
||||||
@@ -49,7 +50,8 @@ class Cons<A> implements ILo<A> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class Mt<A> implements ILo<A> {}
|
class Mt<A> implements ILo<A> {
|
||||||
|
}
|
||||||
|
|
||||||
interface ISequence<X> {
|
interface ISequence<X> {
|
||||||
// Returns the current element in the sequence.
|
// Returns the current element in the sequence.
|
||||||
@@ -78,19 +80,14 @@ class Fibonacci implements ISequence<Integer> {
|
|||||||
public Integer get() {
|
public Integer get() {
|
||||||
int ret; // What to return.
|
int ret; // What to return.
|
||||||
/*
|
/*
|
||||||
|
*
|
||||||
idx pen pre ret
|
* idx pen pre ret 0 0 1 0 1 0 1 1 2 1 1 2 3 1 2 3 4 2 3 5 5 3 5 8
|
||||||
0 0 1 0
|
*
|
||||||
1 0 1 1
|
|
||||||
2 1 1 2
|
|
||||||
3 1 2 3
|
|
||||||
4 2 3 5
|
|
||||||
5 3 5 8
|
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// F(0) = 0; F(1) = 1
|
// F(0) = 0; F(1) = 1
|
||||||
if (this.idx <= 1) ret = this.idx;
|
if (this.idx <= 1)
|
||||||
|
ret = this.idx;
|
||||||
else { // F(n) = F(n-1) + F(n-2)
|
else { // F(n) = F(n-1) + F(n-2)
|
||||||
ret = this.pre + this.pen;
|
ret = this.pre + this.pen;
|
||||||
|
|
||||||
|
@@ -1,109 +1,83 @@
|
|||||||
package mastermind;
|
package mastermind;
|
||||||
|
|
||||||
import tester.Tester;
|
|
||||||
import java.awt.Color;
|
import java.awt.Color;
|
||||||
import java.awt.Image;
|
import java.awt.Image;
|
||||||
import java.util.Random;
|
import java.util.Random;
|
||||||
import javalib.worldimages.*;
|
|
||||||
import javalib.funworld.*;
|
import javalib.funworld.*;
|
||||||
import javalib.worldcanvas.*;
|
import javalib.worldcanvas.*;
|
||||||
|
import javalib.worldimages.*;
|
||||||
|
import tester.Tester;
|
||||||
|
|
||||||
class Examples {
|
class Examples {
|
||||||
ILoInt noInt = new MtInt(),
|
|
||||||
intsOne = new ConsInt(1, new ConsInt(2, new ConsInt(3, noInt)));
|
|
||||||
|
|
||||||
Dot redDot = new Dot(Color.red),
|
ILoInt noInt = new MtInt();
|
||||||
greenDot = new Dot(Color.green),
|
ILoInt intsOne = new ConsInt(1, new ConsInt(2, new ConsInt(3, noInt)));
|
||||||
blueDot = new Dot(Color.blue),
|
|
||||||
reenDot = new Dot(new Color(255, 255, 0));
|
|
||||||
|
|
||||||
ILoDot noDot = new MtDot(),
|
Dot redDot = new Dot(Color.red);
|
||||||
dotsOne = new ConsDot(redDot, new ConsDot(greenDot, new ConsDot(blueDot, noDot)), new Random(0)),
|
Dot greenDot = new Dot(Color.green);
|
||||||
dotsTwo = new ConsDot(redDot, new ConsDot(blueDot, new ConsDot(blueDot, noDot))),
|
Dot blueDot = new Dot(Color.blue);
|
||||||
dotsThree = new ConsDot(reenDot, new ConsDot(reenDot, new ConsDot(reenDot, noDot))),
|
Dot reenDot = new Dot(new Color(255, 255, 0));
|
||||||
exampleDotsOne = new ConsDot(redDot, new ConsDot(greenDot, new ConsDot(blueDot, new ConsDot(greenDot, new ConsDot(redDot, new ConsDot(greenDot, noDot)))))),
|
|
||||||
exampleDotsTwo = new ConsDot(redDot, new ConsDot(blueDot, new ConsDot(greenDot, new ConsDot(greenDot, new ConsDot(blueDot, new ConsDot(blueDot, noDot)))))),
|
ILoDot noDot = new MtDot();
|
||||||
exampleDotsOneNoExact = new ConsDot(greenDot, new ConsDot(blueDot, new ConsDot(redDot, new ConsDot(greenDot, noDot)))),
|
ILoDot dotsOne = new ConsDot(
|
||||||
exampleDotsTwoNoExact = new ConsDot(blueDot, new ConsDot(greenDot, new ConsDot(blueDot, new ConsDot(blueDot, noDot))));
|
redDot,
|
||||||
|
new ConsDot(greenDot, new ConsDot(blueDot, noDot)),
|
||||||
|
new Random(0)
|
||||||
|
);
|
||||||
|
ILoDot dotsTwo = new ConsDot(
|
||||||
|
redDot,
|
||||||
|
new ConsDot(blueDot, new ConsDot(blueDot, noDot))
|
||||||
|
);
|
||||||
|
ILoDot dotsThree = new ConsDot(
|
||||||
|
reenDot,
|
||||||
|
new ConsDot(reenDot, new ConsDot(reenDot, noDot))
|
||||||
|
);
|
||||||
|
ILoDot exampleDotsOne = new ConsDot(
|
||||||
|
redDot,
|
||||||
|
new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(
|
||||||
|
blueDot,
|
||||||
|
new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(redDot, new ConsDot(greenDot, noDot))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
ILoDot exampleDotsTwo = new ConsDot(
|
||||||
|
redDot,
|
||||||
|
new ConsDot(
|
||||||
|
blueDot,
|
||||||
|
new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(blueDot, new ConsDot(blueDot, noDot))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
ILoDot exampleDotsOneNoExact = new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(blueDot, new ConsDot(redDot, new ConsDot(greenDot, noDot)))
|
||||||
|
);
|
||||||
|
ILoDot exampleDotsTwoNoExact = new ConsDot(
|
||||||
|
blueDot,
|
||||||
|
new ConsDot(greenDot, new ConsDot(blueDot, new ConsDot(blueDot, noDot)))
|
||||||
|
);
|
||||||
|
|
||||||
Feedback exampleFeedback = new Feedback(2, 2);
|
Feedback exampleFeedback = new Feedback(2, 2);
|
||||||
|
|
||||||
Game exampleGame = new Game();
|
Game exampleGame = new Game();
|
||||||
|
|
||||||
boolean testILoDotLen(Tester t) {
|
|
||||||
return t.checkExpect(noDot.len(), 0) && t.checkExpect(dotsOne.len(), 3);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotGetnth(Tester t) {
|
|
||||||
return t.checkException(new IllegalArgumentException("Index out of bounds."), noDot, "get", 1)
|
|
||||||
&& t.checkException(new IllegalArgumentException("Index out of bounds."), dotsOne, "get", 3)
|
|
||||||
&& t.checkExpect(dotsOne.get(0), redDot)
|
|
||||||
&& t.checkExpect(dotsOne.get(2), blueDot);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotGen(Tester t) {
|
|
||||||
return t.checkExpect(noDot.gen(219), noDot)
|
|
||||||
&& t.checkExpect(dotsOne.gen(1), new ConsDot(redDot, noDot))
|
|
||||||
&& t.checkExpect(dotsOne.gen(3), new ConsDot(greenDot, new ConsDot(greenDot, new ConsDot(blueDot, noDot))));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotIn(Tester t) {
|
|
||||||
return t.checkExpect(dotsOne.in(blueDot), true)
|
|
||||||
&& t.checkExpect(noDot.in(redDot), false)
|
|
||||||
&& t.checkExpect(dotsThree.in(blueDot), false);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoIntRemove(Tester t) {
|
|
||||||
return t.checkExpect(intsOne.remove(0), new ConsInt(2, new ConsInt(3, noInt)))
|
|
||||||
&& t.checkExpect(intsOne.remove(2), new ConsInt(1, new ConsInt(2, noInt)))
|
|
||||||
&& t.checkException(new IllegalArgumentException("Index out of bounds: cannot remove something from nothing."), intsOne, "remove", 3)
|
|
||||||
&& t.checkException(new IllegalArgumentException("Index out of bounds: cannot remove something from nothing."), noInt, "remove", 0)
|
|
||||||
&& t.checkException(new IllegalArgumentException("Indices must be positive."), intsOne, "remove", -2);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoIntLen(Tester t) {
|
|
||||||
return t.checkExpect(intsOne.len(), 3) && t.checkExpect(noInt.len(), 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoIntSubOne(Tester t) {
|
|
||||||
return t.checkExpect(intsOne.subOne(), new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt))));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotExactIndices(Tester t) {
|
|
||||||
return t.checkException(new IllegalArgumentException("Empty list doesn't exactly match anything."), noDot, "exactIndices", noDot)
|
|
||||||
&& t.checkExpect(dotsOne.exactIndices(dotsOne), new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt))))
|
|
||||||
&& t.checkExpect(dotsOne.exactIndices(dotsTwo), new ConsInt(0, new ConsInt(2, new MtInt())));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotRemove(Tester t) {
|
|
||||||
return t.checkException(new IllegalArgumentException("Index out of bounds."), noDot, "remove", 0)
|
|
||||||
&& t.checkExpect(dotsOne.remove(0), new ConsDot(greenDot, new ConsDot(blueDot, noDot)))
|
|
||||||
&& t.checkExpect(dotsTwo.remove(1), new ConsDot(redDot, new ConsDot(blueDot, noDot)));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotRemoveAll(Tester t) {
|
|
||||||
return t.checkExpect(dotsOne.removeAll(noInt), dotsOne)
|
|
||||||
&& t.checkExpect(dotsOne.removeAll(new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt)))), noDot)
|
|
||||||
&& t.checkExpect(noDot.removeAll(intsOne), noDot)
|
|
||||||
&& t.checkExpect(dotsTwo.removeAll(new ConsInt(1, new ConsInt(2, noInt))), new ConsDot(redDot, noDot));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotCountInexact(Tester t) {
|
|
||||||
return t.checkExpect(noDot.countInexact(noDot), 0)
|
|
||||||
&& t.checkExpect(dotsOne.countInexact(dotsOne), 3)
|
|
||||||
&& t.checkExpect(exampleDotsOneNoExact.countInexact(exampleDotsTwoNoExact), 2);
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testILoDotCompare(Tester t) {
|
|
||||||
return t.checkExpect(exampleDotsOne.compare(exampleDotsTwo), exampleFeedback)
|
|
||||||
&& t.checkExpect(dotsOne.compare(dotsOne), new Feedback(3, 0));
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean testDrawMethods(Tester t) {
|
boolean testDrawMethods(Tester t) {
|
||||||
// WorldImage incomplete = new IncompleteGuess(exampleDotsOne).draw();
|
// WorldImage incomplete = new IncompleteGuess(exampleDotsOne).draw();
|
||||||
//WorldImage guesses = new ConsGuess(new Guess(dotsOne, new Feedback(1, 2)), new ConsGuess(new Guess(dotsTwo, new Feedback(2, 5)), new MtGuess())).draw();
|
// WorldImage guesses = new ConsGuess(new Guess(dotsOne, new Feedback(1, 2)),
|
||||||
Game game = new Game().addGuess(new Guess(dotsOne, exampleFeedback));
|
// new ConsGuess(new Guess(dotsTwo, new Feedback(2, 5)), new MtGuess())).draw();
|
||||||
|
//Game game = new Game().addGuess(new Guess(dotsOne, exampleFeedback));
|
||||||
|
|
||||||
|
/*
|
||||||
WorldImage gameImg = game.draw();
|
WorldImage gameImg = game.draw();
|
||||||
|
|
||||||
int w = (int) gameImg.getWidth();
|
int w = (int) gameImg.getWidth();
|
||||||
@@ -111,25 +85,202 @@ class Examples {
|
|||||||
|
|
||||||
WorldCanvas c = new WorldCanvas(w, h);
|
WorldCanvas c = new WorldCanvas(w, h);
|
||||||
WorldScene s = new WorldScene(w, h);
|
WorldScene s = new WorldScene(w, h);
|
||||||
|
*/
|
||||||
|
|
||||||
return game.launch();
|
return exampleGame.launch();
|
||||||
//c.drawScene(s.placeImageXY(gameImg, w/2, h/2))
|
// c.drawScene(s.placeImageXY(gameImg, w/2, h/2))
|
||||||
//c.drawScene(s.placeImageXY(incomplete, (int) (incomplete.getWidth()/2), 100))
|
// c.drawScene(s.placeImageXY(incomplete, (int) (incomplete.getWidth()/2), 100))
|
||||||
//c.drawScene(s.placeImageXY(exampleFeedback.draw(), 100, 100))
|
// c.drawScene(s.placeImageXY(exampleFeedback.draw(), 100, 100))
|
||||||
//c.drawScene(s.placeImageXY(redDot.draw(), 100, 100))
|
// c.drawScene(s.placeImageXY(redDot.draw(), 100, 100))
|
||||||
//c.drawScene(s.placeImageXY(dotsOne.draw(), 250, 250))
|
// c.drawScene(s.placeImageXY(dotsOne.draw(), 250, 250))
|
||||||
//&& c.show();
|
// && c.show();
|
||||||
//true;
|
// true;
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotLen(Tester t) {
|
||||||
|
return t.checkExpect(noDot.len(), 0) && t.checkExpect(dotsOne.len(), 3);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotGetnth(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException("Index out of bounds."),
|
||||||
|
noDot,
|
||||||
|
"get",
|
||||||
|
1
|
||||||
|
) &&
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException("Index out of bounds."),
|
||||||
|
dotsOne,
|
||||||
|
"get",
|
||||||
|
3
|
||||||
|
) &&
|
||||||
|
t.checkExpect(dotsOne.get(0), redDot) &&
|
||||||
|
t.checkExpect(dotsOne.get(2), blueDot)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotGen(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(noDot.gen(219), noDot) &&
|
||||||
|
t.checkExpect(dotsOne.gen(1), new ConsDot(redDot, noDot)) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsOne.gen(3),
|
||||||
|
new ConsDot(
|
||||||
|
greenDot,
|
||||||
|
new ConsDot(greenDot, new ConsDot(blueDot, noDot))
|
||||||
|
)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotIn(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(dotsOne.in(blueDot), true) &&
|
||||||
|
t.checkExpect(noDot.in(redDot), false) &&
|
||||||
|
t.checkExpect(dotsThree.in(blueDot), false)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoIntRemove(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(
|
||||||
|
intsOne.remove(0),
|
||||||
|
new ConsInt(2, new ConsInt(3, noInt))
|
||||||
|
) &&
|
||||||
|
t.checkExpect(
|
||||||
|
intsOne.remove(2),
|
||||||
|
new ConsInt(1, new ConsInt(2, noInt))
|
||||||
|
) &&
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException(
|
||||||
|
"Index out of bounds: cannot remove something from nothing."
|
||||||
|
),
|
||||||
|
intsOne,
|
||||||
|
"remove",
|
||||||
|
3
|
||||||
|
) &&
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException(
|
||||||
|
"Index out of bounds: cannot remove something from nothing."
|
||||||
|
),
|
||||||
|
noInt,
|
||||||
|
"remove",
|
||||||
|
0
|
||||||
|
) &&
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException("Indices must be positive."),
|
||||||
|
intsOne,
|
||||||
|
"remove",
|
||||||
|
-2
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoIntLen(Tester t) {
|
||||||
|
return t.checkExpect(intsOne.len(), 3) && t.checkExpect(noInt.len(), 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoIntSubOne(Tester t) {
|
||||||
|
return t.checkExpect(
|
||||||
|
intsOne.subOne(),
|
||||||
|
new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt)))
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotExactIndices(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException(
|
||||||
|
"Empty list doesn't exactly match anything."
|
||||||
|
),
|
||||||
|
noDot,
|
||||||
|
"exactIndices",
|
||||||
|
noDot
|
||||||
|
) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsOne.exactIndices(dotsOne),
|
||||||
|
new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt)))
|
||||||
|
) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsOne.exactIndices(dotsTwo),
|
||||||
|
new ConsInt(0, new ConsInt(2, new MtInt()))
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotRemove(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkException(
|
||||||
|
new IllegalArgumentException("Index out of bounds."),
|
||||||
|
noDot,
|
||||||
|
"remove",
|
||||||
|
0
|
||||||
|
) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsOne.remove(0),
|
||||||
|
new ConsDot(greenDot, new ConsDot(blueDot, noDot))
|
||||||
|
) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsTwo.remove(1),
|
||||||
|
new ConsDot(redDot, new ConsDot(blueDot, noDot))
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotRemoveAll(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(dotsOne.removeAll(noInt), dotsOne) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsOne.removeAll(
|
||||||
|
new ConsInt(0, new ConsInt(1, new ConsInt(2, noInt)))
|
||||||
|
),
|
||||||
|
noDot
|
||||||
|
) &&
|
||||||
|
t.checkExpect(noDot.removeAll(intsOne), noDot) &&
|
||||||
|
t.checkExpect(
|
||||||
|
dotsTwo.removeAll(new ConsInt(1, new ConsInt(2, noInt))),
|
||||||
|
new ConsDot(redDot, noDot)
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotCountInexact(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(noDot.countInexact(noDot), 0) &&
|
||||||
|
t.checkExpect(dotsOne.countInexact(dotsOne), 3) &&
|
||||||
|
t.checkExpect(
|
||||||
|
exampleDotsOneNoExact.countInexact(exampleDotsTwoNoExact),
|
||||||
|
2
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean testILoDotCompare(Tester t) {
|
||||||
|
return (
|
||||||
|
t.checkExpect(
|
||||||
|
exampleDotsOne.compare(exampleDotsTwo),
|
||||||
|
exampleFeedback
|
||||||
|
) &&
|
||||||
|
t.checkExpect(dotsOne.compare(dotsOne), new Feedback(3, 0))
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class Util {
|
class Util {
|
||||||
|
|
||||||
static int scale = 2;
|
static int scale = 2;
|
||||||
static int fontSz = 24 * scale;
|
static int fontSz = 24 * scale;
|
||||||
static int gapW = 4 * scale; // The gap between objects.
|
static int gapW = 4 * scale; // The gap between objects.
|
||||||
|
|
||||||
// Drawing methods.
|
// Drawing methods.
|
||||||
static WorldImage gap = new RectangleImage(gapW, gapW, "outline", new Color(0, 0, 0, 0));
|
static WorldImage gap = new RectangleImage(
|
||||||
|
gapW,
|
||||||
|
gapW,
|
||||||
|
"outline",
|
||||||
|
new Color(0, 0, 0, 0)
|
||||||
|
);
|
||||||
|
|
||||||
static WorldImage pairGap(WorldImage img1, WorldImage img2) {
|
static WorldImage pairGap(WorldImage img1, WorldImage img2) {
|
||||||
return new BesideAlignImage(AlignModeY.MIDDLE, img1, gap, img2);
|
return new BesideAlignImage(AlignModeY.MIDDLE, img1, gap, img2);
|
||||||
}
|
}
|
||||||
@@ -139,7 +290,10 @@ class Util {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static WorldImage strPair(String str1, String str2) {
|
static WorldImage strPair(String str1, String str2) {
|
||||||
return pairGap(new TextImage(str1, fontSz, Color.black), new TextImage(str2, fontSz, Color.black));
|
return pairGap(
|
||||||
|
new TextImage(str1, fontSz, Color.black),
|
||||||
|
new TextImage(str2, fontSz, Color.black)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int pairgapW = 2 * 16 * scale + gapW;
|
static int pairgapW = 2 * 16 * scale + gapW;
|
||||||
@@ -147,7 +301,14 @@ class Util {
|
|||||||
|
|
||||||
// A game state.
|
// A game state.
|
||||||
class Game extends World {
|
class Game extends World {
|
||||||
static ILoDot DEFAULTDOTS = new ConsDot(new Dot(Color.RED), new ConsDot(new Dot(Color.GREEN), new ConsDot(new Dot(Color.BLUE), new MtDot())));
|
|
||||||
|
static ILoDot DEFAULTDOTS = new ConsDot(
|
||||||
|
new Dot(Color.RED),
|
||||||
|
new ConsDot(
|
||||||
|
new Dot(Color.GREEN),
|
||||||
|
new ConsDot(new Dot(Color.BLUE), new MtDot())
|
||||||
|
)
|
||||||
|
);
|
||||||
static GameConf DEFAULTCONF = new GameConf(true, 5, 5, DEFAULTDOTS);
|
static GameConf DEFAULTCONF = new GameConf(true, 5, 5, DEFAULTDOTS);
|
||||||
|
|
||||||
GameConf conf; // The game's configuration.
|
GameConf conf; // The game's configuration.
|
||||||
@@ -157,8 +318,17 @@ class Game extends World {
|
|||||||
boolean done; // Is the game over?
|
boolean done; // Is the game over?
|
||||||
boolean won; // Did they player win?
|
boolean won; // Did they player win?
|
||||||
|
|
||||||
Game(GameConf conf, ILoDot solution, int guessesLeft, ILoGuess guesses, boolean won, boolean done) {
|
Game(
|
||||||
if (this.won && !this.done) throw new IllegalArgumentException("Can't win before you've finished playing.");
|
GameConf conf,
|
||||||
|
ILoDot solution,
|
||||||
|
int guessesLeft,
|
||||||
|
ILoGuess guesses,
|
||||||
|
boolean won,
|
||||||
|
boolean done
|
||||||
|
) {
|
||||||
|
if (this.won && !this.done) throw new IllegalArgumentException(
|
||||||
|
"Can't win before you've finished playing."
|
||||||
|
);
|
||||||
this.conf = conf;
|
this.conf = conf;
|
||||||
this.solution = solution;
|
this.solution = solution;
|
||||||
this.won = won;
|
this.won = won;
|
||||||
@@ -168,21 +338,51 @@ class Game extends World {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Convenience constructor using default config and starting values.
|
// Convenience constructor using default config and starting values.
|
||||||
Game() { this(DEFAULTCONF, DEFAULTCONF.options.gen(DEFAULTCONF.len), DEFAULTCONF.nguesses, new MtGuess(), false, false); }
|
Game() {
|
||||||
|
this(
|
||||||
|
DEFAULTCONF,
|
||||||
|
DEFAULTCONF.options.gen(DEFAULTCONF.len),
|
||||||
|
DEFAULTCONF.nguesses,
|
||||||
|
new MtGuess(),
|
||||||
|
false,
|
||||||
|
false
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
public WorldScene makeScene() {
|
public WorldScene makeScene() {
|
||||||
WorldScene bg = this.getEmptyScene();
|
WorldImage img = this.draw();
|
||||||
WorldImage dot = new Dot(Color.RED).draw();
|
int w = (int) img.getWidth(), h = (int) img.getHeight();
|
||||||
return bg.placeImageXY(dot , (int)dot.getWidth(), (int)dot.getHeight());
|
WorldScene bg = new WorldScene(w, h);
|
||||||
|
return bg.placeImageXY(img, (int) w / 2, (int) h / 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean launch() {
|
boolean launch() {
|
||||||
return this.bigBang(100, 100);
|
return this.bigBang(this.calcW(), this.calcH());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate the width of the window without drawing anything.
|
||||||
|
int calcW() {
|
||||||
|
return (
|
||||||
|
(this.conf.len * Dot.r * 2) + // The width of all the dots.
|
||||||
|
((this.conf.len + 1) * Util.gapW) + // The width of all the spaces between the dots.
|
||||||
|
Util.fontSz * 2 + // The width of the feedback numbers.
|
||||||
|
Util.gapW // The width of the gap between the feedback numbers.
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate the height of the window without drawing anything.
|
||||||
|
int calcH() {
|
||||||
|
return ((this.conf.nguesses + 2) * Dot.r * 2); // Width of all the guess rows, plus the two rows above and below (for solution and options respectively.)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw the current game state.
|
// Draw the current game state.
|
||||||
WorldImage draw() {
|
WorldImage draw() {
|
||||||
return new AboveAlignImage(AlignModeX.LEFT, this.draw_sol(), this.draw_guesses(), this.draw_options());
|
return new AboveAlignImage(
|
||||||
|
AlignModeX.LEFT,
|
||||||
|
this.draw_sol(),
|
||||||
|
this.draw_guesses(),
|
||||||
|
this.draw_options()
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Draw the solution.
|
// Draw the solution.
|
||||||
@@ -198,7 +398,12 @@ class Game extends World {
|
|||||||
|
|
||||||
// Draw the hidden answer.
|
// Draw the hidden answer.
|
||||||
WorldImage draw_sol_hid() {
|
WorldImage draw_sol_hid() {
|
||||||
return new RectangleImage(this.solution.getW(), 2*Dot.r, OutlineMode.SOLID, Color.BLACK);
|
return new RectangleImage(
|
||||||
|
this.solution.getW(),
|
||||||
|
2 * Dot.r,
|
||||||
|
OutlineMode.SOLID,
|
||||||
|
Color.BLACK
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
WorldImage draw_guesses() {
|
WorldImage draw_guesses() {
|
||||||
@@ -210,27 +415,51 @@ class Game extends World {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Convenience methods for testing -- not part of program.
|
// Convenience methods for testing -- not part of program.
|
||||||
Game win() { return new Game(this.conf, this.solution, this.guessesLeft, this.guesses, true, true); }
|
Game win() {
|
||||||
Game addGuess(Guess guess) { return new Game(this.conf, this.solution, this.guessesLeft, new ConsGuess(guess, this.guesses), this.won, this.done); }
|
return new Game(
|
||||||
|
this.conf,
|
||||||
|
this.solution,
|
||||||
|
this.guessesLeft,
|
||||||
|
this.guesses,
|
||||||
|
true,
|
||||||
|
true
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Game addGuess(Guess guess) {
|
||||||
|
return new Game(
|
||||||
|
this.conf,
|
||||||
|
this.solution,
|
||||||
|
this.guessesLeft,
|
||||||
|
new ConsGuess(guess, this.guesses),
|
||||||
|
this.won,
|
||||||
|
this.done
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// A game configuration.
|
// A game configuration.
|
||||||
class GameConf {
|
class GameConf {
|
||||||
|
|
||||||
boolean dups; // Whether duplicates are allowed.
|
boolean dups; // Whether duplicates are allowed.
|
||||||
int len; // The length of the sequence to be guessed.
|
int len; // The length of the sequence to be guessed.
|
||||||
int nguesses; // Number of guesses the player is allowed.
|
int nguesses; // Number of guesses the player is allowed.
|
||||||
ILoDot options; // The dots of which the solution is comprised.
|
ILoDot options; // The dots of which the solution is comprised.
|
||||||
|
|
||||||
GameConf(boolean dups, int len, int nguesses, ILoDot options) {
|
GameConf(boolean dups, int len, int nguesses, ILoDot options) {
|
||||||
if (len <= 0)
|
if (len <= 0) throw new IllegalArgumentException(
|
||||||
throw new IllegalArgumentException("Length of the solution must be greater than 0.");
|
"Length of the solution must be greater than 0."
|
||||||
if (nguesses <= 0)
|
);
|
||||||
throw new IllegalArgumentException("Must provide the player some guesses.");
|
if (nguesses <= 0) throw new IllegalArgumentException(
|
||||||
|
"Must provide the player some guesses."
|
||||||
|
);
|
||||||
int oplen = options.len();
|
int oplen = options.len();
|
||||||
if (oplen <= 0)
|
if (oplen <= 0) throw new IllegalArgumentException(
|
||||||
throw new IllegalArgumentException("Must have dot options to guess with.");
|
"Must have dot options to guess with."
|
||||||
if (!dups && len > oplen)
|
);
|
||||||
throw new IllegalArgumentException("Cant create solution of that length without duplicates.");
|
if (!dups && len > oplen) throw new IllegalArgumentException(
|
||||||
|
"Cant create solution of that length without duplicates."
|
||||||
|
);
|
||||||
|
|
||||||
this.dups = dups;
|
this.dups = dups;
|
||||||
this.len = len;
|
this.len = len;
|
||||||
@@ -245,6 +474,7 @@ interface ILoGuess {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class ConsGuess implements ILoGuess {
|
class ConsGuess implements ILoGuess {
|
||||||
|
|
||||||
Guess guess;
|
Guess guess;
|
||||||
ILoGuess nxt;
|
ILoGuess nxt;
|
||||||
|
|
||||||
@@ -259,12 +489,15 @@ class ConsGuess implements ILoGuess {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class MtGuess implements ILoGuess {
|
class MtGuess implements ILoGuess {
|
||||||
|
|
||||||
public WorldImage draw() {
|
public WorldImage draw() {
|
||||||
return new EmptyImage();
|
return new EmptyImage();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// A guess.
|
||||||
class Guess {
|
class Guess {
|
||||||
|
|
||||||
ILoDot guess; // The dots the user entered.
|
ILoDot guess; // The dots the user entered.
|
||||||
Feedback feedback; // The feedback returned.
|
Feedback feedback; // The feedback returned.
|
||||||
|
|
||||||
@@ -278,7 +511,9 @@ class Guess {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// A guess in the midst of being entered.
|
||||||
class IncompleteGuess {
|
class IncompleteGuess {
|
||||||
|
|
||||||
ILoDot guessSoFar;
|
ILoDot guessSoFar;
|
||||||
|
|
||||||
IncompleteGuess(ILoDot guessSoFar) {
|
IncompleteGuess(ILoDot guessSoFar) {
|
||||||
@@ -290,9 +525,10 @@ class IncompleteGuess {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Feedback for a guess.
|
||||||
class Feedback {
|
class Feedback {
|
||||||
int exact,
|
|
||||||
inexact;
|
int exact, inexact;
|
||||||
|
|
||||||
Feedback(int exact, int inexact) {
|
Feedback(int exact, int inexact) {
|
||||||
this.exact = exact;
|
this.exact = exact;
|
||||||
@@ -300,38 +536,56 @@ class Feedback {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Feedback add(Feedback other) {
|
Feedback add(Feedback other) {
|
||||||
int otherExact = other.exact,
|
int otherExact = other.exact, otherInexact = other.inexact;
|
||||||
otherInexact = other.inexact;
|
|
||||||
|
|
||||||
return new Feedback(this.exact + otherExact, this.inexact + otherInexact);
|
return new Feedback(
|
||||||
|
this.exact + otherExact,
|
||||||
|
this.inexact + otherInexact
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
WorldImage draw() {
|
WorldImage draw() {
|
||||||
return Util.strPair(String.valueOf(this.exact), String.valueOf(this.exact));
|
return Util.strPair(
|
||||||
|
String.valueOf(this.exact),
|
||||||
|
String.valueOf(this.exact)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// A list of dots.
|
||||||
interface ILoDot {
|
interface ILoDot {
|
||||||
int len(); // Get length.
|
int len(); // Get length.
|
||||||
|
|
||||||
Dot get(int n); // Get nth element.
|
Dot get(int n); // Get nth element.
|
||||||
|
|
||||||
ILoDot remove(int n); // Remove nth element.
|
ILoDot remove(int n); // Remove nth element.
|
||||||
|
|
||||||
ILoDot removeAll(ILoInt indices); // Remove element at each index.
|
ILoDot removeAll(ILoInt indices); // Remove element at each index.
|
||||||
|
|
||||||
ILoDot gen(int n); // Generate randomized list.
|
ILoDot gen(int n); // Generate randomized list.
|
||||||
|
|
||||||
boolean match(Color col); // Do the colors match?
|
boolean match(Color col); // Do the colors match?
|
||||||
|
|
||||||
boolean in(Dot dot); // Is the dot in here?
|
boolean in(Dot dot); // Is the dot in here?
|
||||||
|
|
||||||
Feedback compare(ILoDot other); // Compare two lists & give feedback.
|
Feedback compare(ILoDot other); // Compare two lists & give feedback.
|
||||||
|
|
||||||
ILoInt exactIndices(ILoDot other); // Get indices of exact matches.
|
ILoInt exactIndices(ILoDot other); // Get indices of exact matches.
|
||||||
|
|
||||||
ILoInt exactIndicesHelper(ILoDot other, int i);
|
ILoInt exactIndicesHelper(ILoDot other, int i);
|
||||||
int countInexact(ILoDot other); // Get the number of inexact matches. Must be fed exact match-free lists to be accurate.
|
|
||||||
|
int countInexact(ILoDot other); // Get the number of inexact matches. Must be fed exact match-free lists to be
|
||||||
|
// accurate.
|
||||||
|
|
||||||
int countInexactHelper(ILoDot other, ILoDot seen);
|
int countInexactHelper(ILoDot other, ILoDot seen);
|
||||||
|
|
||||||
WorldImage draw(); // Draw the dots.
|
WorldImage draw(); // Draw the dots.
|
||||||
|
|
||||||
int getW(); // Get the total width, in pixels, of the list.
|
int getW(); // Get the total width, in pixels, of the list.
|
||||||
}
|
}
|
||||||
|
|
||||||
class ConsDot implements ILoDot {
|
class ConsDot implements ILoDot {
|
||||||
|
|
||||||
Random rand;
|
Random rand;
|
||||||
Dot dot;
|
Dot dot;
|
||||||
ILoDot nxt;
|
ILoDot nxt;
|
||||||
@@ -341,24 +595,54 @@ class ConsDot implements ILoDot {
|
|||||||
this.dot = dot;
|
this.dot = dot;
|
||||||
this.nxt = nxt;
|
this.nxt = nxt;
|
||||||
}
|
}
|
||||||
ConsDot(Dot dot, ILoDot nxt) { this(dot, nxt, new Random()); }
|
|
||||||
|
ConsDot(Dot dot, ILoDot nxt) {
|
||||||
|
this(dot, nxt, new Random());
|
||||||
|
}
|
||||||
|
|
||||||
public ILoDot gen(int n) {
|
public ILoDot gen(int n) {
|
||||||
return n <= 0 ? new MtDot() : new ConsDot(this.get(this.rand.nextInt(this.len())), this.gen(n - 1));
|
return n <= 0
|
||||||
|
? new MtDot()
|
||||||
|
: new ConsDot(
|
||||||
|
this.get(this.rand.nextInt(this.len())),
|
||||||
|
this.gen(n - 1)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Dot get(int n) {
|
public Dot get(int n) {
|
||||||
if (n == 0) return this.dot;
|
if (n == 0) return this.dot;
|
||||||
else return this.nxt.get(n - 1);
|
else return this.nxt.get(n - 1);
|
||||||
}
|
}
|
||||||
public boolean in(Dot dot) { return dot.equals(this.dot) || this.nxt.in(dot); }
|
|
||||||
public int len() { return 1 + this.nxt.len(); }
|
|
||||||
public boolean match(Color col) { return col.equals(this.dot.c); }
|
|
||||||
|
|
||||||
public WorldImage draw() { return new BesideAlignImage(AlignModeY.PINHOLE, this.dot.draw(), Util.gap, this.nxt.draw()); }
|
public boolean in(Dot dot) {
|
||||||
public int getW() { return this.len() * Dot.r * 2; }
|
return dot.equals(this.dot) || this.nxt.in(dot);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int len() {
|
||||||
|
return 1 + this.nxt.len();
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean match(Color col) {
|
||||||
|
return col.equals(this.dot.c);
|
||||||
|
}
|
||||||
|
|
||||||
|
public WorldImage draw() {
|
||||||
|
return new BesideAlignImage(
|
||||||
|
AlignModeY.PINHOLE,
|
||||||
|
this.dot.draw(),
|
||||||
|
Util.gap,
|
||||||
|
this.nxt.draw()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getW() {
|
||||||
|
return this.len() * Dot.r * 2;
|
||||||
|
}
|
||||||
|
|
||||||
public Feedback compare(ILoDot other) {
|
public Feedback compare(ILoDot other) {
|
||||||
if (this.len() != other.len()) throw new IllegalArgumentException("Cannot compare different lengthed lists.");
|
if (this.len() != other.len()) throw new IllegalArgumentException(
|
||||||
|
"Cannot compare different lengthed lists."
|
||||||
|
);
|
||||||
|
|
||||||
ILoInt exactIndices = this.exactIndices(other);
|
ILoInt exactIndices = this.exactIndices(other);
|
||||||
|
|
||||||
@@ -371,14 +655,16 @@ class ConsDot implements ILoDot {
|
|||||||
return new Feedback(exact, inexact);
|
return new Feedback(exact, inexact);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ILoInt exactIndices(ILoDot other) { return this.exactIndicesHelper(other, 0); }
|
public ILoInt exactIndices(ILoDot other) {
|
||||||
|
return this.exactIndicesHelper(other, 0);
|
||||||
|
}
|
||||||
|
|
||||||
public ILoInt exactIndicesHelper(ILoDot other, int i) {
|
public ILoInt exactIndicesHelper(ILoDot other, int i) {
|
||||||
// Stop after reaching the end of the list.
|
// Stop after reaching the end of the list.
|
||||||
if (i == this.len()) return new MtInt();
|
if (i == this.len()) return new MtInt();
|
||||||
|
|
||||||
return this.get(i).equals(other.get(i)) ?
|
return this.get(i).equals(other.get(i))
|
||||||
new ConsInt(i, this.exactIndicesHelper(other, i + 1))
|
? new ConsInt(i, this.exactIndicesHelper(other, i + 1))
|
||||||
: this.exactIndicesHelper(other, i + 1);
|
: this.exactIndicesHelper(other, i + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -388,14 +674,22 @@ class ConsDot implements ILoDot {
|
|||||||
|
|
||||||
public int countInexactHelper(ILoDot other, ILoDot seen) {
|
public int countInexactHelper(ILoDot other, ILoDot seen) {
|
||||||
if (seen.in(this.dot)) {
|
if (seen.in(this.dot)) {
|
||||||
return this.nxt.countInexactHelper(other, new ConsDot(this.dot, seen));
|
return this.nxt.countInexactHelper(
|
||||||
|
other,
|
||||||
|
new ConsDot(this.dot, seen)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
return (other.in(this.dot) ? 1 : 0) + this.nxt.countInexactHelper(other, new ConsDot(this.dot, seen));
|
return (
|
||||||
|
(other.in(this.dot) ? 1 : 0) +
|
||||||
|
this.nxt.countInexactHelper(other, new ConsDot(this.dot, seen))
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
public ILoDot remove(int n) {
|
public ILoDot remove(int n) {
|
||||||
if (n < 0) throw new IllegalArgumentException("Indices must be positive.");
|
if (n < 0) throw new IllegalArgumentException(
|
||||||
|
"Indices must be positive."
|
||||||
|
);
|
||||||
|
|
||||||
if (n == 0) return this.nxt;
|
if (n == 0) return this.nxt;
|
||||||
else return new ConsDot(this.dot, this.nxt.remove(n - 1));
|
else return new ConsDot(this.dot, this.nxt.remove(n - 1));
|
||||||
@@ -408,50 +702,106 @@ class ConsDot implements ILoDot {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class MtDot implements ILoDot {
|
class MtDot implements ILoDot {
|
||||||
public ILoDot gen(int n) { return new MtDot(); }
|
|
||||||
public Dot get(int n) { throw new IllegalArgumentException("Index out of bounds."); }
|
public ILoDot gen(int n) {
|
||||||
public int len() { return 0; }
|
return new MtDot();
|
||||||
public WorldImage draw() { return new EmptyImage(); }
|
}
|
||||||
public int getW() { return 0; }
|
|
||||||
public Feedback compare(ILoDot other) { return new Feedback(0, 0); }
|
public Dot get(int n) {
|
||||||
public boolean match(Color col) { return false; }
|
throw new IllegalArgumentException("Index out of bounds.");
|
||||||
public boolean in(Dot dot) { return false; }
|
}
|
||||||
public ILoInt exactIndices(ILoDot other) {
|
|
||||||
throw new IllegalArgumentException("Empty list doesn't exactly match anything.");
|
public int len() {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public WorldImage draw() {
|
||||||
|
return new EmptyImage();
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getW() {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Feedback compare(ILoDot other) {
|
||||||
|
return new Feedback(0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean match(Color col) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean in(Dot dot) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt exactIndices(ILoDot other) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
"Empty list doesn't exactly match anything."
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt exactIndicesHelper(ILoDot other, int i) {
|
||||||
|
return new MtInt();
|
||||||
|
}
|
||||||
|
|
||||||
|
public int countInexact(ILoDot other) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int countInexactHelper(ILoDot other, ILoDot seen) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoDot remove(int n) {
|
||||||
|
throw new IllegalArgumentException("Index out of bounds.");
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoDot removeAll(ILoInt indices) {
|
||||||
|
return this;
|
||||||
}
|
}
|
||||||
public ILoInt exactIndicesHelper(ILoDot other, int i) { return new MtInt(); }
|
|
||||||
public int countInexact(ILoDot other) { return 0; }
|
|
||||||
public int countInexactHelper(ILoDot other, ILoDot seen) { return 0; }
|
|
||||||
public ILoDot remove(int n) { throw new IllegalArgumentException("Index out of bounds."); }
|
|
||||||
public ILoDot removeAll(ILoInt indices) { return this; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// A dot.
|
||||||
class Dot {
|
class Dot {
|
||||||
|
|
||||||
static int r = 16 * Util.scale;
|
static int r = 16 * Util.scale;
|
||||||
static OutlineMode outlineMode = OutlineMode.SOLID;
|
static OutlineMode outlineMode = OutlineMode.SOLID;
|
||||||
|
|
||||||
Color c;
|
Color c;
|
||||||
|
|
||||||
Dot(Color c) { this.c = c; }
|
Dot(Color c) {
|
||||||
|
this.c = c;
|
||||||
|
}
|
||||||
|
|
||||||
// Draw the dot.
|
// Draw the dot.
|
||||||
WorldImage draw() { return new CircleImage(r, outlineMode, this.c); }
|
WorldImage draw() {
|
||||||
|
return new CircleImage(r, outlineMode, this.c);
|
||||||
|
}
|
||||||
|
|
||||||
// Get the width of the dot.
|
// Get the width of the dot.
|
||||||
int getW() { return 2 * r; }
|
int getW() {
|
||||||
|
return 2 * r;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// A list of integers.
|
// A list of integers.
|
||||||
interface ILoInt {
|
interface ILoInt {
|
||||||
int len(); // Get the length of the list.
|
int len(); // Get the length of the list.
|
||||||
|
|
||||||
ILoInt remove(int n); // Remove the nth element of the list.
|
ILoInt remove(int n); // Remove the nth element of the list.
|
||||||
|
|
||||||
boolean isEmpty(); // Is it empty?
|
boolean isEmpty(); // Is it empty?
|
||||||
|
|
||||||
int first(); // Get the first value.
|
int first(); // Get the first value.
|
||||||
|
|
||||||
ILoInt rest(); // Get the rest value.
|
ILoInt rest(); // Get the rest value.
|
||||||
|
|
||||||
ILoInt subOne(); // Subtract 1 from every int.
|
ILoInt subOne(); // Subtract 1 from every int.
|
||||||
}
|
}
|
||||||
|
|
||||||
class ConsInt implements ILoInt {
|
class ConsInt implements ILoInt {
|
||||||
|
|
||||||
int val;
|
int val;
|
||||||
ILoInt nxt;
|
ILoInt nxt;
|
||||||
|
|
||||||
@@ -460,22 +810,63 @@ class ConsInt implements ILoInt {
|
|||||||
this.nxt = nxt;
|
this.nxt = nxt;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int len() { return 1 + this.nxt.len(); }
|
public int len() {
|
||||||
public ILoInt remove(int n) {
|
return 1 + this.nxt.len();
|
||||||
if (n < 0) throw new IllegalArgumentException("Indices must be positive.");
|
}
|
||||||
return n == 0 ? this.nxt : new ConsInt(this.val, this.nxt.remove(n - 1));
|
|
||||||
|
public ILoInt remove(int n) {
|
||||||
|
if (n < 0) throw new IllegalArgumentException(
|
||||||
|
"Indices must be positive."
|
||||||
|
);
|
||||||
|
return n == 0
|
||||||
|
? this.nxt
|
||||||
|
: new ConsInt(this.val, this.nxt.remove(n - 1));
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isEmpty() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int first() {
|
||||||
|
return this.val;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt rest() {
|
||||||
|
return this.nxt;
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt subOne() {
|
||||||
|
return new ConsInt(this.val - 1, this.nxt.subOne());
|
||||||
}
|
}
|
||||||
public boolean isEmpty() { return false; }
|
|
||||||
public int first() { return this.val; }
|
|
||||||
public ILoInt rest() { return this.nxt; }
|
|
||||||
public ILoInt subOne() { return new ConsInt(this.val - 1, this.nxt.subOne()); }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class MtInt implements ILoInt {
|
class MtInt implements ILoInt {
|
||||||
public int len() { return 0; }
|
|
||||||
public ILoInt remove(int n) { throw new IllegalArgumentException("Index out of bounds: cannot remove something from nothing."); }
|
public int len() {
|
||||||
public boolean isEmpty() { return true; }
|
return 0;
|
||||||
public int first() { throw new IllegalArgumentException("Cannot get first element in a list without any."); }
|
}
|
||||||
public ILoInt rest() { throw new IllegalArgumentException("Cannot get rest of empty list."); }
|
|
||||||
public ILoInt subOne() { return this; }
|
public ILoInt remove(int n) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
"Index out of bounds: cannot remove something from nothing."
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isEmpty() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int first() {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
"Cannot get first element in a list without any."
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt rest() {
|
||||||
|
throw new IllegalArgumentException("Cannot get rest of empty list.");
|
||||||
|
}
|
||||||
|
|
||||||
|
public ILoInt subOne() {
|
||||||
|
return this;
|
||||||
|
}
|
||||||
}
|
}
|
Reference in New Issue
Block a user