问题出在i-1这里
当 i
等于0的时候,candidates[i-1]
和used[i-1]
会试图访问数组的负索引,这是未定义的行为,可能导致运行时错误。
你需要确保在进行这种操作之前检查 i
是否大于0:
if(i > 0 && candidates[i]==candidates[i-1]&&used[i-1]==0)
总结
在大多数情况下,这种类型的错误信息表示尝试访问了数组的某个位置,而这个位置不在数组的有效范围内,也就是说,你的代码试图进行越界访问。当试图访问未初始化的数组元素或者超出数组范围的下标时,都可能发生这种错误。
具体来看
runtime error: addition of unsigned offset to 0x603000000070 overflowed to 0x60300000006c (stl_vector.h)
这是一个运行时错误,它表示在执行到stl_vector.h
文件中的某一行时,发生了溢出。具体来说,这是一个无符号整数溢出错误,说明程序尝试将一个正值(无符号偏移)加到一个地址上,但结果却比原地址小,这表明发生了溢出。
一般情况下,这可能是由于在访问vector
的元素时使用了负索引,而在C++中,vector
的索引必须是非负的,所以导致了越界错误。尤其是在这个代码中,如果 i
为0,那么 candidates[i-1]
和 used[i-1]
就会尝试访问负索引,导致这个错误。所以必须在访问这些元素之前先检查 i
是否大于0。
修改后的代码
40.组合总和Ⅱ
class Solution {
public:
void backtracking(vector<int>&path,vector<vector<int>>&result,vector<int>& candidates,int sum,int target,vector<int>&used,int startIndex){
//终止条件
if(sum>target){
return;
}
if(sum==target){
result.push_back(path);
return;
}
//单层搜索
for(int i=startIndex;i<candidates.size();i++){
if(i>=1&&candidates[i]==candidates[i-1]&&used[i-1]==0){
continue; //直接不处理,跳到for循环的下一个
}
sum += candidates[i];
path.push_back(candidates[i]);
//记录use过当前的i
used[i]=1;
//开始递归
backtracking(path,result,candidates,sum,target,used,i+1);
//回溯,重置use
sum -= candidates[i];
path.pop_back();
used[i]=0;
}
}
vector<vector<int>> combinationSum2(vector<int>& candidates, int target) {
vector<int>path;
vector<vector<int>>result;
//注意这种带有初始大小和初始值的vector数组定义方式!需要访问used下标所以必须初始化
vector<int>used(candidates.size(),0);
int sum=0;
int startIndex=0;
sort(candidates.begin(),candidates.end());
backtracking(path,result,candidates,sum,target,used,startIndex);
return result;
}
};