给定一个含有
n
个正整数的数组和一个正整数target
。找出该数组中满足其总和大于等于
target
的长度最小的 连续子数组[numsl, numsl+1, ..., numsr-1, numsr]
,并返回其长度。如果不存在符合条件的子数组,返回0
。输入:target = 7, nums = [2,3,1,2,4,3] 输出:2 解释:子数组 [4,3] 输入:target = 4, nums = [1,4,4] 输出:1
int minSubArrayLen(int target, int* nums, int numsSize) {
int l=0,r=0;
int sum=0;
int ans=INT_MAX;
while(r=target){
ans=fmin(ans,r-l+1);
sum-=nums[l];
l++;
}
r++;
}
return ans==INT_MAX?0:ans;
}
给你一个整数数组
nums
和一个整数k
,请你返回子数组内所有元素的乘积严格小于k
的连续子数组的数目。输入:nums = [10,5,2,6], k = 100 输出:8 解释:8 个乘积小于 100 的子数组分别为:[10]、[5]、[2],、[6]、[10,5]、[5,2]、[2,6]、[5,2,6]。 需要注意的是 [10,5,2] 并不是乘积小于 100 的子数组。
int numSubarrayProductLessThanK(int* nums, int numsSize, int k) {
int l=0,r=0;
int sum=1;
int ans=0;
while(r=k){
sum/=nums[l];
l++;
}
ans+=r-l+1;
r++;
}
return ans;
}
给定一个字符串
s
,请你找出其中不含有重复字符的 最长连续子字符串 的长度。输入: s = "abcabcbb" 输出: 3 解释: 因为无重复字符的最长子字符串是 "abc",所以其长度为 3。 输入: s = "bbbbb" 输出: 1 解释: 因为无重复字符的最长子字符串是 "b"所以其长度为 1。
此题不是只有字母,因此无法通过,有除字母以外的字符之外出现的话需要用map进行记录。
int lengthOfLongestSubstring(char * s){
if(s=="") return 0;
int flag[128]={0};
int l=0,r=0;
int ans=0;
int n=strlen(s);
while(r1){
flag[s[l]-'a']--;
l++;
}
if(l
c++版本:
class Solution {
public:
int lengthOfLongestSubstring(string s) {
int n=s.size();
int left=0;
int answer=0;
set st;
for(int right=0;right
给你一个整数数组
arr
,请你删除一个子数组(可以为空),使得arr
中剩下的元素是 非递减 的。一个子数组指的是原数组中连续的一个子序列。请你返回满足题目要求的最短子数组的长度。输入:arr = [1,2,3,10,4,2,3,5] 输出:3 解释:我们需要删除的最短子数组是 [10,4,2] ,长度为 3 。剩余元素形成非递减数组 [1,2,3,3,5] 。 另一个正确的解为删除子数组 [3,10,4] 。
int findLengthOfShortestSubarray(int* arr, int arrSize){
int r=arrSize-1;
while(r&&arr[r-1]<=arr[r]){
r--;
}
//当前数列已经是递增的
if(r==0) return 0;
int ans=r;
//枚举左区间起点
for(int l=0;l==0||arr[l-1]<=arr[l];++l){
while(r
给定一个二进制数组
nums
和一个整数k
,如果可以翻转最多k
个0
,则返回 数组中连续1
的最大个数 。输入:nums = [1,1,1,0,0,0,1,1,1,1,0], K = 2 输出:6 解释:[1,1,1,0,0,1,1,1,1,1,1] 粗体数字从 0 翻转到 1,最长的子数组长度为 6。输入:nums = [0,0,1,1,0,0,1,1,1,0,1,1,0,0,0,1,1,1,1], K = 3 输出:10 解释:[0,0,1,1,1,1,1,1,1,1,1,1,0,0,0,1,1,1,1] 粗体数字从 0 翻转到 1,最长的子数组长度为 10。
int longestOnes(int* nums, int numsSize, int k) {
int l=0,r=0;
int zero=0;
int ans=0;
while(rk){
if(nums[l]==0) zero--;
l++;
}
ans=fmax(ans,r-l+1);
r++;
}
return ans;
}
有一个只含有
'Q', 'W', 'E', 'R'
四种字符,且长度为n
的字符串。假如在该字符串中,这四个字符都恰好出现
n/4
次,那么它就是一个「平衡字符串」。给你一个这样的字符串s
,请通过「替换一个子串」的方式,使原字符串s
变成一个「平衡字符串」。你可以用和「待替换子串」长度相同的 任何 其他字符串来完成替换。请返回待替换子串的最小可能长度。如果原字符串自身就是一个平衡字符串,则返回
0
。输入:s = "QWER" 输出:0 解释:s 已经是平衡的了。输入:s = "QQWE" 输出:1 解释:我们需要把一个 'Q' 替换成 'R',这样得到的 "RQWE" (或 "QRWE") 是平衡的。
int balancedString(char* s) {
int hash[26]={0};
int l=0,r=0;
int len=strlen(s);
int n=len/4;
int ans=len;
//记录每个字母出现的次数
for(int i=0;i
给你一个整数数组
nums
和一个整数x
。每一次操作时,你应当移除数组nums
最左边或最右边的元素,然后从x
中减去该元素的值。请注意,需要 修改 数组以供接下来的操作使用。如果可以将x
恰好 减到0
,返回 最小操作数 ;否则,返回-1
。输入:nums = [1,1,4,2,3], x = 5 输出:2 解释:最佳解决方案是移除后两个元素,将 x 减到 0 。
方法一:逆向思维+双指针
把问题转换成「从 nums 中移除一个最长的子数组,使得剩余元素的和为 x。换句话说,要从 nums 中找最长的子数组,其元素和等于 s−x,这里 s 为 nums 所有元素之和。
int minOperations(int* nums, int numsSize, int x) {
//从nums中移除一个最长的子数组,使得剩余元素的和为x
int target=0;
for(int i=0;itarget){
sum-=nums[l];
l++;
}
if(sum==target){
ans=fmax(ans,r-l+1);
}
}
return ans<0?-1:numsSize-ans;
}
给你一个整数数组
nums
,判断是否存在三元组[nums[i], nums[j], nums[k]]
满足i != j
、i != k
且j != k
,同时还满足nums[i] + nums[j] + nums[k] == 0
。请你返回所有和为
0
且不重复的三元组。注意:答案中不可以包含重复的三元组。
输入:nums = [-1,0,1,2,-1,-4] 输出:[[-1,-1,2],[-1,0,1]] 解释: nums[0] + nums[1] + nums[2] = (-1) + 0 + 1 = 0 。 nums[1] + nums[2] + nums[4] = 0 + 1 + (-1) = 0 。 nums[0] + nums[3] + nums[4] = (-1) + 2 + (-1) = 0 。 不同的三元组是 [-1,0,1] 和 [-1,-1,2] 。 注意,输出的顺序和三元组的顺序并不重要。
class Solution {
public:
vector> threeSum(vector& nums) {
vector> result;
sort(nums.begin(), nums.end());
for (int i = 0; i < nums.size(); i++) {
// 排序之后如果第一个元素已经大于零,那么无论如何组合都不可能凑成三元组,直接返回结果就可以了
if (nums[i] > 0) {
return result;
}
if (i > 0 && nums[i] == nums[i - 1]) {//去重
continue;
}
int left = i + 1;
int right = nums.size() - 1;
while (right > left) {
if (nums[i] + nums[left] + nums[right] > 0) right--;
else if (nums[i] + nums[left] + nums[right] < 0) left++;
else {
result.push_back(vector{nums[i], nums[left], nums[right]});
// 去重逻辑应该放在找到一个三元组之后,对b 和 c去重
while (right > left && nums[right] == nums[right - 1]) right--;
while (right > left && nums[left] == nums[left + 1]) left++;
// 找到答案时,双指针同时收缩
right--;
left++;
}
}
}
return result;
}
};
给你一个下标从 1 开始的整数数组
numbers
,该数组已按 非递减顺序排列 ,请你从数组中找出满足相加之和等于目标数target
的两个数。如果设这两个数分别是numbers[index1]
和numbers[index2]
,则1 <= index1 < index2 <= numbers.length
。以长度为 2 的整数数组
[index1, index2]
的形式返回这两个整数的下标index1
和index2
。你可以假设每个输入 只对应唯一的答案 ,而且你 不可以 重复使用相同的元素。
你所设计的解决方案必须只使用常量级的额外空间。
输入:numbers = [2,7,11,15], target = 9 输出:[1,2] 解释:2 与 7 之和等于目标数 9 。因此 index1 = 1, index2 = 2 。返回 [1, 2] 。
int* twoSum(int* numbers, int numbersSize, int target, int* returnSize) {
int *res=malloc(sizeof(int)*2);
*returnSize=2;
int l=0,r=numbersSize-1;
while(ltarget){
r--;
}else{
res[0]=l+1;res[1]=r+1;
return res;
}
}
return res;
}
给定一个长度为
n
的整数数组height
。有n
条垂线,第i
条线的两个端点是(i, 0)
和(i, height[i])
。找出其中的两条线,使得它们与x
轴共同构成的容器可以容纳最多的水。返回容器可以储存的最大水量。输入:[1,8,6,2,5,4,8,3,7] 输出:49 解释:图中垂直线代表输入数组 [1,8,6,2,5,4,8,3,7]。在此情况下,容器能够容纳水(表示为蓝色部分)的最大值为 49。
int maxArea(int* height, int heightSize) {
int mmax=0;
int i=0,j=heightSize-1;
while(immax) mmax=cur;
if(height[i]