数组理论基础
数组是存放在连续内存空间上的相同类型数据的集合。
因为数组的在内存空间的地址是连续的,所以我们在删除或者增添元素的时候,就难免要移动其他元素的地址。
在C++中二维数组是连续分布的
java中二维数组不是连续分布的
704. 二分查找
34.35先不做了。
一开始我想的是直接用循环就能够找下表标,因为如果使用二分法的话需要对数组先进行一个排序,但这道题给定的数组是已经排序过了的,所以能够直接使用。并且,对于大容量的数据来说,二分法的时间复杂度低。
比如给定的 nums = [-1,0,3,5,9,12], target = 9。
在这里数组长度为6,所以我们设左节点为0时,右节点为5(6-1即nums.size()-1)确定好节点后,确定中点,mid = (right - left) / 2 + left=2。num在这里等于3。3与9不等且小于9,保留的是右半部分,所以令left=mid+1,我认为mid+1是因为mid所在位置已经判断过了所以不需要涵盖在接下来是数组中。于是得到新数组为[5,9,12]两边left为3对应数值为5,right不变为5对应数值为12。重复mid = (right - left) / 2 + left=4。mid为4,nums[mid]=9为查询数值,返回。
class Solution {
public:
int search(vector<int>& nums, int target) {
int left = 0, right = nums.size() - 1;
while(left <= right){
int mid = (right - left) / 2 + left;
int num = nums[mid];
if (num == target) {
return mid;
} else if (num > target) {
right = mid - 1;
} else {
left = mid + 1;
}
}
return -1;
}
};
对于二分法有两种[left, right]&[left, right),上述方法是[left, right]的。另一种以后再说…
27. 移除元素
我的垃圾代码如下:(错误,未能运行)
思路是需要在原数组进行变更,那么我就用val直接与数组进行比较。比如说nums = [3,2,2,3], val = 3。首先,知道数组长度,l=4,所以字符地址为0,1,2,3。将val与nums对比时,当i=1时,两者相等,此时我想判断数组最后一位是否与2相等,如果不等我将最后一位的值覆盖在i=1的位置上,同时将l缩小为3,若最后一位等于 val那么就将l直接缩小为3,然后再判断倒数第二位是否与val相等。
思路没问题,又读了一遍题发现返回数组长度就可以了,于是简单修改代码就能够运行了。
class Solution {
public:
int removeElement(vector<int>& nums, int val) {
int l,end;
l =nums.size()-1;
end=nums.size()-1;
int i=0;
while(i<=l)
{
if(nums[i]==val)//判断当前数是否与val相等
{
while(i<=l)
{
if(nums[l]!=val)//判断末端是否为val
{ nums[i]=nums[l];
l--;
break;
}
else
l--;
}}
else
i++;
}
return l+1;//返回数组长度
}
};
但是执行的效果不太好,看一下标准答案
这有一个快慢指针法
class Solution {
public:
int removeElement(vector<int>& nums, int val) {
int slowIndex = 0;
for (int fastIndex = 0; fastIndex < nums.size(); fastIndex++) {
if (val != nums[fastIndex]) {
nums[slowIndex++] = nums[fastIndex];
}
}
return slowIndex;
}
};
我理解的就是重新赋值,快指针与慢指针始终保持着一前一后的状态,如果快指针等于val,那么此时不需要将该值赋值给慢指针,其余情况慢指针都等于快指针,所以最后返回的是慢指针的l。