我正在做一个名为Thirty in Java的骰子游戏。我有一个数组,其中包含骰子的值,如[1,3,4,5,5,6]。从那个阵列我希望能够找到给出总和的每个组,但每个骰子只能计算一次。
例如,如果我有数组[1,3,4,5,5,6]并且想要找到每个等于12的组,那将给我举例如1 + 5 + 6 = 12和3 + 4 + 5 = 12
如[1,1,1,1,2,6]这样的例子,我会得到1 + 1 + 1 + 1 + 2 + 6 = 12。
总会有6个骰子,但我寻找的总和可以是4到12之间的任何一个。
有人可以帮帮我吗?我真的没有任何代码可以提供,只会让人感到困惑,根本无法提供帮助。
答案 0 :(得分:0)
我有一个算法可以解决您的问题,但您必须根据自己的需要进行调整。 不幸的是,我不知道它是否是任何特定已知数据结构的一部分。
简而言之,我会说它会以二进制位置转换你的数组并在其上循环,从没有标记任何项目到标记所有项目的位置。
递增二进制数组,它只标记标记的位置。我们将能够总结所有可能的组合。
TEST 1
鉴于您的参数:
结果是:
Position: 011010 // means the sum of item in position 1,2,4 (3 + 4 + 5 = 12)
Position: 011100 // means the sum of item in position 1,2,3 (3 + 4 + 5 = 12)
Position: 100011 // means the sum of item in position 0,4,5 (1 + 5 + 6 = 12)
Position: 100101 // means the sum of item in position 0,3,5 (1 + 5 + 6 = 12)
TEST 2
鉴于您的参数:
结果是:
Position: 111111 // means the sum of item in position 0,1,2,3,4,5 (1+1+1+1+2+6 = 12)
代码可以改进,但如下所示,简单地打印" 1"到要求总和的位置,得到所需的数字。
public class Algorithm {
public static void main(String[] args) {
Algorithm checkSum = new Algorithm();
Integer[] array = {1, 3, 4, 5, 5, 6};
Integer sum = 12;
checkSum.find(array, sum);
System.out.println("------------------");
Integer[] array2 = {1, 1, 1, 1, 2, 6};
Integer sum2 = 12;
checkSum.find(array2, sum2);
}
private void find(Integer[] array, Integer sum) {
// This could be replaced by a StringUtils lib to fill with "1" the size of the array
String maxBinary = "";
for (int i=0; i<array.length; i++) {
maxBinary += "1";
}
int maxDecimal = Integer.parseInt(maxBinary, 2);
// This will iterate from "000000" to "111111"
for (int i=0; i<=maxDecimal; i++) {
String binaryNumber = lpad(Integer.toBinaryString(i), array.length);
int checkSum = 0;
for (int j=0; j<binaryNumber.length(); j++) {
if ("1".equals(binaryNumber.substring(j,j+1))) {
checkSum += array[j];
}
}
// This is the check to see if the sum is the desired one
if (sum == checkSum) {
System.out.println("Positions: " + binaryNumber);
}
}
}
/**
* This is a simple LPAD function to add zeros to the left of the string.
*/
private String lpad(String text, Integer size) {
String regex = "%0"+ size + "d";
return String.format(regex, Integer.parseInt(text));
}
}
&#13;
希望它有所帮助!
答案 1 :(得分:0)
这里没有经过极好的测试,也许有点天真的解决方案。我使用整数列表,因为我不喜欢数组,对不起!
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import org.junit.Before;
import org.junit.Test;
public class PickNumbersTest {
private List<Integer> numbers;
@Before
public void before() {
Integer[] ints = new Integer[] { 1, 3, 4, 5, 5, 6 };
numbers = new ArrayList<>();
numbers.addAll(Arrays.asList(ints));
}
@Test
public void test() {
PickNumbers p = new PickNumbers();
List<List<Integer>> result = p.pick(12, numbers);
System.out.println(result);
}
}
import java.util.ArrayList;
import java.util.List;
public class PickNumbers {
public List<List<Integer>> pick(final int sum, final List<Integer> values) {
// make a copy to avoid making changes to passed in List
List<Integer> numbers = copy(values);
List<List<Integer>> results = new ArrayList<List<Integer>>();
while (!pickSingle(sum, numbers).isEmpty()) {
List<Integer> currentResult = pickSingle(sum, numbers);
results.add(currentResult);
currentResult.forEach(i -> numbers.remove(i));
}
return results;
}
protected List<Integer> pickSingle(final int sum, final List<Integer> values) {
int rest = sum;
List<Integer> result = new ArrayList<>();
Picker p = new Picker(values);
while (rest > 0 && p.hasNext()) {
int i = p.next();
if (i > rest) {
p.remove();
} else if (i == rest) {
result.add(i);
return result;
} else { // i < rest
result.add(i);
p.remove();
rest = rest - i;
}
}
return new ArrayList<>();
}
private List<Integer> copy(final List<Integer> values) {
List<Integer> copy = new ArrayList<Integer>();
copy.addAll(values);
return copy;
}
}
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class Picker {
private List<Integer> values = new ArrayList<Integer>();
public Picker(final List<Integer> values) {
this.values.addAll(values);
this.values.sort(null);
Collections.reverse(this.values);
}
public int next() {
return values.get(0);
}
public void remove() {
values.remove(0);
}
public boolean hasNext() {
return values.size() > 0;
}
}