Java数组常用操作及相关leetcode算法题
1、创建
已知数组元素
int [] array = {1, 2, 3}
int [] array = new int[]{1, 2, 3};
已知数组长度
int [] array = new int[3];
使用ArrayList,不用确定长度和元素
AraayList<Integer>
list = new ArrayList<>();
2、添加元素
前三种创建数组的方法要添加元素,需要新建一个长度更长的数组,这里使用ArrayList的方法
默认在尾部添加元素
list.add(99);
一般默认尾部是有空间添加元素的,时间复杂度为O(1)
如果尾部没有空间添加元素,需要开辟新空间,将之前的元素移过去然后添加元素,时间复杂度是O(N)
在指定索引添加元素
list.add(3, 99);
时间复杂度是O(N),因为需要移动插入位置之后的元素
3、访问元素 均为O(1)
使用下标访问
int array1 = array[1];
ArrayList使用索引访问
list.get(1);
4、更新元素 均为O(1)
使用下标更新
array[1] = 11;
ArrayList使用索引更新
list.set(1, 11);
5、删除元素
使用前三种创建方法创建的数组删除很麻烦,要删除元素一般使用ArrayList来创建数组
list.remove(3);
这里的3不是索引,是要删除的元素值
时间复杂度是O(N),因为底层要移动元素
6、获取数组长度
前三种创建方法使用属性length
int length = array.length;
ArrayList使用方法size()
int length = list.size();
时间复杂度是O(1),因为创建数组时会有一个对应的count变量,增删时会随之改变,调用上述属性或方法返回的是该变量,而没有去遍历
7、遍历数组 均为O(N)
使用下标获取
for(int i = 0; i < array.length; i++) {
int a = array[i];
}
ArrayList使用索引获取
for(int i = 0; i < list.size(); i++) {
int a = list.get(i);
}
8、查找元素 判断是否存在 均为O(N)
使用下标查找
for(int i = 0; i < array.length; i++) {
if(array[i] == target) {
存在
}
}
使用ArrayList的contains方法查找
boolean b = list.contains(target);
if(b)
存在
9、数组排序
前三种方法创建的数组
Arrays.sort(array);
没有从大到小对应的方法
法1 倒着读
法2 改为Integer[] array;可以使用Arrays.sort(T[], Collections.reverseOrder());
ArrayList创建的数组
Collections.sort(list);
从大到小 Collections.sort(T[], Collections.reverseOrder());
这里的时间复杂度是O(NlogN),十大排序算法最快的就是O(NlogN)
10、数组相关leetcode
No.485 最大连续1的个数
思路:定义变量count记录当前连续1的个数,result记录最大连续1的个数
遍历数组,如果当前元素为1,count++;否则元素为0,如果count>result,则result=count
遍历完之后再比较一次,如果count>result,则result=count
class Solution {
public int findMaxConsecutiveOnes(int[] nums) {
if(nums == null || nums.length == 0)
return 0;
int result = 0;
int count = 0;
for(int i = 0; i < nums.length; i++) {
if(nums[i] == 1) {
count++;
} else {
if(count > result)
result = count;
count = 0;
}
}
if(count > result) {
result = count;
}
return result;
}
}
No.283 移动零
思路:定义变量count记录当前要移动到目标位置的下标,从0开始,即第一个非零元素要移动到下标为0的位置,第二个非零元素要移动到下标为1的位置。遍历数组,如果当前元素等于0,就跳过,进行下一次循环;否则将其移动到位置0,count++为1;第二次循环,如果当前元素为0就进行第三次循环,否则将元素移动到位置1,以此类推。直到循环结束,所有非零元素都按顺序移动到了数组的前半部分,当前count一定指向非零元素的下一个位置,因为count只有在元素非零时才会+1,否则不变。将count和之后的位置均置为0即可。
class Solution {
public void moveZeroes(int[] nums) {
int count = 0;//第几个非零元素要放到的下标
for(int i = 0; i < nums.length; i++) {
if(nums[i] == 0) {
continue;
} else {
nums[count] = nums[i];
count++;
}
}
for(int i = count; i < nums.length; i++) {
nums[i] = 0;
}
}
}
No.27 移除元素
思路:和上一题几乎一样。定义变量count记录元素到移动到的位置。遍历数组,如果当前元素等于目标值,进入下一次循环;否则将当前元素移动到count指向的位置,count++。遍历结束后,所有非目标值的元素都被移动到了数组的前半部分。count指向最后一个非目标值元素的下一个位置,因为非目标值元素的下标从0开始,所有count表示的就是非目标值元素的个数,即移除后数组的长度。
class Solution {
public int removeElement(int[] nums, int val) {
if(nums == null || nums.length ==0)
return 0;
int count = 0;
for(int i = 0; i < nums.length; i++) {
if(nums[i] == val) {
continue;
} else {
nums[count] = nums[i];
count++;
}
}
return count;
}
}