我正在尝试用 Java 编写一个递归函数,以确定如何完成飞镖游戏。基本上,你最多有 3 支飞镖,你必须以双打结束。
如果你不知道 Double Out 完成的 Darts x01 游戏规则,这个问题很难理解……让我试着解释一下。为简单起见,我暂时不考虑公牛的眼睛。
规则:
1) 你有三个飞镖,你可以在 1 到 20 号投掷
2) 单打可以有单打、双打或三打
例如,您可以打:单 20 = 20 分或双 20 = 40 分或三联 20 = 60 分
3)一回合最多可以得到180分(3x三倍20=3*60=180)。任何高于 180 的东西都是不可能的。这并不意味着低于 180 IS 的任何事情都是可能的。例如 179 也是不可能的,因为下一个最好的分数是triple20+triple20+triple19 = 167
4) 通常,您从 501 开始,然后投掷 3 支飞镖,直到您正好剩下 0 分。
5) 现在,在 Double Out 中,要求最后一镖击中 Double Out
例如,如果您还剩 180 分,您将无法完成,因为您的最后一镖必须是双镖。所以最大值(忽略靶心)=triple20 + Triple20 + double20 = 160 如果你的分数是 16,你可以通过击中双 8 来完成使用 1 镖。另一个例子,如果你的分数是 61,你可以打三重17 + 双5(= 51 + 10)
当前代码
无论如何,以下是我到目前为止所拥有的。我知道这远非我所需要的,但无论我尝试什么,我总是卡住。也许有人可以分享他对另一种方法的想法
private class Score{
int number; // the actual number, can be 1...20
int amount; // multiplier, can be 1, 2 or 3
public Score(int number, int amount){
this.number = number; // the actual number, can be 1...20
this.amount = amount; // multiplier, can be 1, 2 or 3
}
public int value()
{
return number * amount; // the actual score
}
public void increment()
{
if(this.amount == 0)
this.amount = 1;
this.number++;
if(this.number >= 20)
{
this.number = 0;
this.amount++;
if(this.amount >= 3)
this.amount = 3;
}
}
}
public ArrayList<Score> canFinish(int desired, ArrayList<Score> score){
// If this is the case -> we have bingo
if(eval(score) == desired) return score;
// this is impossible -> return null
if(eval(score) > 170) return null;
// I can't figure out this part!!
Score dart3 = score.remove(2);
Score dart2 = score.remove(1);
if(dart2.eval() < 60){
dart2.increment();
}
else if(dart3.eval() < 60){
dart3.increment();
}
score.add(dart2);
score.add(dart3);
return canFinish(desired, score);
}
public int eval(ArrayList<Score> scores)
{
int total = 0;
for(Score score : scores){
total += score.value();
}
return total;
}
我想简单地打电话:
ArrayList<Score> dartsNeeded = new ArrayList<Score>();
dartsNeeded.add(new Score(16, 2)); // Add my favourite double
dartsNeeded.add(new Score(0, 0));
dartsNeeded.add(new Score(0, 0));
// and call the function
dartsNeeded = canFinish(66, dartsNeeded);
// In this example the returned values would be:
// [[16,2],[17,2],[0,0]] -> 2*16 + 2*17 + 0*0 = 66
// So I can finish, by throwing Double 17 + Double 16
因此,如果不可能完成,该函数将返回 null,但如果有任何可能的完成,我会用 3 个飞镖来获取 ArrayList,我需要达到我想要的分数......
简短的摘要
问题是上面的代码只有助于找到 1 个 dart,而不是两个 dart 的组合。所以 canFinish(66, darts) 有效 -> 但 canFinish(120, darts) 给出了 StackOverflow 异常。对于 120,我希望得到类似 Triple20、double14、double16 或任何其他有效组合的东西。