LeetCode977.有序数组的平方
题目链接:977.有序数组的平方
暴力解法是先对数组进行平方,然后用快排排序,时间复杂度为O(nlogn)。要实现O(n)的时间复杂度,可以使用双指针的方法。原来数组是非递减的,说明绝对值从外侧到中心是由大变小的,那么平方后由外侧向内也是非递增的。希望平方后的数组非递减,可以利用双指针,从外侧向内遍历,比较两侧平方中比较大的数,把它填到新的数组中。
int k=nums.size()-1;
int i=0;int j=nums.size()-1;
vector<int> result(nums.size(),0);
while(i<=j){
if(nums[i]*nums[i]>nums[j]*nums[j]){
result[k]=nums[i]*nums[i];
k--;
i++;
}
else{
result[k]=nums[j]*nums[j];
k--;
j--;
}
}
return result;
LeetCode209.长度最小的数组
暴力算法,双层for循环,外层遍历定起点i,内层遍历从i开始,定第一个符合要求的子串的终点j,与当前最短的比较,由于j不断要返回i的位置,时间复杂度为O(n²)。可以采用双指针法,指针j正向扫描定结尾(以上一次i作开头,满足sum >= target),向后移动指针i寻找最短子串,一旦i不符合条件就break,让j继续前移。指针j扫描数组,指针i找到[ i_before, j ]区间的最短长度子串,i和j都不用后移,时间复杂度为O(n)。
int i=0;
int result=INT_MAX;//最短长度
int sum=0;//计算和
int lenth;//计算长度
for(int j=0;j<nums.size();j++){
sum += nums[j];
while(sum >= target){ //子串中可能包含符合要求的更短的子串
lenth = j-i+1;
result = result < lenth? result:lenth;
sum -= nums[i];
i++;
}
}
if(result<INT_MAX)return result;
else return 0;
LeetCode59.螺旋矩阵
题目链接:59.螺旋矩阵
模拟顺时针画矩阵的过程:
- 填充上行从左到右
- 填充右列从上到下
- 填充下行从右到左
- 填充左列从下到上
由外向内画圈,要注意区间,每一个循环中都是左闭右开区间,每一次循环行列都有一个固定。还要注意如果n是单数,中间的位置要另外填。
自己写的时候出现的问题:忘记缩小圈,每次画圈结束都需要offset-1
int loop=n/2;//圈数
int startx=0,starty=0;//每圈的起点
int i=0,j=0;
int offset=1;//用来缩小圈
int num=1;//表示填在矩阵里的数
while(loop--){
i=startx;
j=starty;
for(;j<n-offset;j++){//从左到右
res[startx][j]=num;
num++;
}
for(;i<n-offset;i++){//从上到下
res[i][j]=num;
num++;
}
for(;j>offset-1;j--){//从右到左
res[i][j]=num;
num++;
}
for(;i>offset-1;i--){//从下到上
res[i][j]=num;
num++;
}
startx++;
starty++;//更新起点
offset++;//缩小圈
}
if(n%2){//如果是奇数,中间值还要另外赋值
res[startx][starty]=n*n;
}
return res;