盛最多水的容器
原理:ij指针从两边各自滑动,滑动的条件是解题的关键,解决时间复杂度较高的问题
public int solution(int[] height) {
// int ans=0, x=0;
// for(int i=0; i<height.length-1; i++) {
// for(int j=i+1; j<height.length; j++) {
// x = (j-i)*Math.min(height[i], height[j]);
// ans = x>ans?x:ans;
// }
// }//暴力求解时间复杂度高
//自己的思想陷入到ij指针只能从一编开始动,有时候应该转换一下思想,ij指针分别从头尾开始动,就可能得到时间复杂度较小的较优解
int ans=0, i=0, j=height.length-1, x=0;
while(i<j) {
x = (j-i)*Math.min(height[i], height[j]);
ans = x>ans?x:ans;
//每次移动height较小的指针,因为木桶效应
//面积取决于指针的距离与值小的值乘积,如果值大的值向内移动,距离一定减小,面积也一定减小,是没有意义的
if(height[i]<height[j])i++;
else j--;
}
return ans;
}
三数之和
原理思想:先固定一个数值,然后再利用剪枝的思想去找剩下两个和固定数值和为0的两个数,利用ij双指针不断逼近,直至i>=j。其中的去重思想很重要,是解题的关键步骤,也是降低时间复杂度的一种方法(避免重复的查找)。
public List<List<Integer>> solution(int[] nums) {
Arrays.sort(nums);//排序
int k=0, i=1, j=nums.length-1;
List<List<Integer>> result=new LinkedList<>();
for( ; k<nums.length-2; k++) {//为什么是-2,因为ij需要占据一个位置,到最后一次循环k=length-3, i=length-2, j=length-1
//最小的都大于0,没有找的意义了
if(nums[k]>0)break;
//固定的数num[k]和num[k-1]相同,代表num[k-1]的结果已经找过了,用k去重,跳出这次循环
if(k>0 && nums[k] == nums[k-1])continue;
//每次k循环结束都要重新对ij赋值
i=k+1;
j=nums.length-1;
//结束条件,ij指针指向同一数值
while(i<j) {
//sum和小于0,就将i指针向右移动,增加sum
if(nums[k]+nums[i]+nums[j]<0) {
i++;
}
else if (nums[k]+nums[i]+nums[j]>0) {
j--;
}
else {
List<Integer> res=new LinkedList<>();
res.add(nums[k]);
res.add(nums[i]);
res.add(nums[j]);
result.add(res);
//用ij去重,和为0后就要缩小指针范围:i++,j--
//但是可能出现nums[]中的数值相等的情况,这个结果已经考虑过了,为什么?
//因为在一次循环中,nums[k],nums[i]是确定的,如果下次i++,得到的nums[i+1]==nums[i],那么再次找到的nums[j]的值一定是重复的
while(i<j && nums[i]==nums[i+1])i++;
while(i<j && nums[j]==nums[j-1])j--;
i++;j--;
}
}
}
return result;
}
LinkedList和ArrayList的区别
ArrayList 和 LinkedList 是 List 接口的两种不同实现。ArrayList 内部使用的动态数组来存储元素,LinkedList 内部使用的双向链表来存储元素,这也是 ArrayList 和 LinkedList 最本质的区别。
需要注意的是,如果列表很大很大,ArrayList 和 LinkedList 在内存的使用上也有所不同。LinkedList 的每个元素都有更多开销,因为要存储上一个和下一个元素的地址。ArrayList 没有这样的开销,其更加轻量级。
但是,ArrayList 占用的内存在声明的时候就已经确定了(默认大小为 10),不管实际上是否添加了元素,因为复杂对象的数组会通过 null 来填充。LinkedList 在声明的时候不需要指定大小,元素增加或者删除时大小随之改变。
另外,ArrayList 只能用作列表;LinkedList 可以用作列表或者队列,因为它还实现了 Deque接口
还要注意new一个list对象要用linkedlist或者arraylist,因为list是接口
List<Integer> aIntegers=new LinkedList<>();
List<Integer> aIntegers=new ArrayList<>()
快速打印list元素
List<String> list = new ArrayList<String>();
list.add("a");
list.add("b");
list.add("c");
System.out.println(Arrays.toString(list.toArray()));