C++ 如何操纵字符数组导致堆栈溢出?
如果有明显的缺陷,我很抱歉。我对内存相当陌生,所以我对堆栈溢出的工作原理有一些了解,据我所知,我所做的任何事情都不会导致堆栈溢出。我所做的就是改变字符串中的字符 我知道数组是指针,但是更改值会导致堆栈溢出吗 以下是相关功能:C++ 如何操纵字符数组导致堆栈溢出?,c++,stack-overflow,C++,Stack Overflow,如果有明显的缺陷,我很抱歉。我对内存相当陌生,所以我对堆栈溢出的工作原理有一些了解,据我所知,我所做的任何事情都不会导致堆栈溢出。我所做的就是改变字符串中的字符 我知道数组是指针,但是更改值会导致堆栈溢出吗 以下是相关功能: char base[] = "aaaaa"; void changeLetters(int position) { // Stack overflow happens around here if (base[position] != 'z') {
char base[] = "aaaaa";
void changeLetters(int position) { // Stack overflow happens around here
if (base[position] != 'z') {
base[position]++;
}
// When I include a cout here, I also get a stack overflow
if (position == 4 && base[position] != 'z') {
changeLetters(position);
}
else if (base[position] == 'z' && position != 0) {
base[position] = 'a';
changeLetters(position - 1);
}
else if (position < 4) {
changeLetters(position + 1);
}
}
char base[]=“aaaaa”;
void changeLetters(int位置){//堆栈溢出发生在这附近
如果(基本[位置]!='z'){
基本[位置]+;
}
//当我在这里包括cout时,我也会得到堆栈溢出
如果(位置==4&&base[位置]!='z'){
更改字母(位置);
}
else if(基本[位置]='z'&&position!=0){
基本[位置]=“a”;
更改字母(位置-1);
}
否则如果(位置<4){
更改字母(位置+1);
}
}
当没有std::cout
时,我得到
passwordCracker.exe中0x767C3210(KernelBase.dll)处未处理的异常:0xC00000FD:堆栈溢出(参数:0x00000001、0x01002FFC)
否则
passwordCracker.exe中0x009C38B9处未处理的异常:0xC00000FD:堆栈溢出(参数:0x00000001、0x006D2F8C)
编辑:
该函数在主循环中调用。传递的值是字符串(4)的长度,它通过它来工作。我没有提到的一件奇怪的事情是,如果我循环使用少量的字母(a、b、c、d),它会很好地工作,但是如果我让它循环使用字母表,我只会收到堆栈溢出。您的代码正在迭代由字母表
a-z
组成的所有长度5
的字符串。这本身不是问题,但是您必须确保最大调用深度不会太大
在changeretters
的每次迭代中,您最多增加一个字母一次,然后再次调用changeretters
,并且您最多进行一次这样的调用
因此,您的调用图是完全线性的,对于每个26^5
字符串,您都在进行另一个深度递归调用,因此末尾的调用堆栈将非常大。问题是,这是一个非常大的数字26^5=11881376
,可能很容易大于您可能使用的堆栈空间
您需要将线性调用图变成一个带有分支的调用图,例如,在当前字符的位置上使用循环,而不是每次调用
changeLetters
。递归不是无限的,而是很深的。深到足以炸掉这堆东西
函数每次递增一个字母时都使用递归。由于有5个字符,每个字符包含26个可能的值,因此递归的深度为265=11881376级。我不确定你的堆栈有多大,但它不够大,无法处理那么多级别。因此会出现堆栈溢出
切换到使用嵌套循环的迭代解决方案。如何声明/定义
base
?(请)如何调用此函数?为位置传递的值是多少?@NathanOliver它是一个字符数组!抱歉,我在第一次写问题时忘了提。我几乎可以肯定你有一个无限递归,我只是不知道这些方法在做什么……顺便说一句,“我知道数组是指针”,不,它们不是。