题目:
1、输入一个递增排序的数组和一个数字S,在数组中查找两个数,是的他们的和正好是S,如果有多对数字的和等于S,输出两个数的乘积最小的。
2、输入一个正数s,输出所有和为S的连续正数序列。序列内按照从小至大的顺序,序列间按照开始数字从小到大的顺序。
思路:有点类似快速排序中的partition函数,都是定义两个引用变量,分别指向序列中的两端,依次判断和是否为s,同时不断更新两个引用变量。
注意:注意一些编程中的细节,详见注释。
/*
* 1、
* 参考快速排序中的partition函数
* 设置两个指针分别指向数组的首位和末位,依次判断和是否为s
* 若和小于s,i++;若和大于s,j--
*/
public ArrayList<Integer> findNumbersWithSum(int [] array,int sum) {
ArrayList<Integer> list = new ArrayList<>();
int i = 0;
int j = array.length - 1;
while(i < j){
while(array[i] + array[j] < sum && i < j){
i++;
}
while(array[i] + array[j] > sum && i < j){
j--;
}
if(array[i] + array[j] == sum){
list.add(array[i]);
list.add(array[j]);
break;
}
}
return list;
}
/**
* 2、
* 仍然定义两个引用,一个指向连续整数序列的最小值,一个指向连续整数序列的最大值
* 若和小于sum,则增大j;若和大于sum,则减小i
*/
public ArrayList<ArrayList<Integer>> findContinuousSequence(int sum) {
ArrayList<ArrayList<Integer>> r = new ArrayList<>();
ArrayList<Integer> subStr = new ArrayList<>();
int i = 1;
int j = 2;
int s = i + j;
while(s != sum || i <= sum/2){
while(s < sum && i <= sum/2){
j++;
s = s + j;
}
while(s > sum && i <= sum/2){
s = s - i; //注意顺序问题,在i++之前减
i++;
}
if(s == sum){
for (int k = i; k <= j; k++) {
subStr.add(k);
}
r.add(new ArrayList<>(subStr));
subStr = new ArrayList<>(); //清空subStr
i++; //每找出一个序列,再继续找下一个序列的时候,注意i,j,s三个变量的变化情况
j++;
s = s - i + 1 + j;
}
if(i > sum/2)
break;
}
return r;
}