Я учился о буфере
#include <iostream>
using namespace std;
int main()
{
char input[3];
for(int i=0;i<100;i++){
cin>>input[i];
}
return 0;
}
Программа включается и выключается без остановки и без признаков переполнения (протестировано в 2 коробках Linux)
То же самое произойдет, если я поменяюсь:
cin>>input[i];
с :
input[i]='a';
Это переполнение буфера, а не переполнение стека. Этот код разрушит стек, но вы можете увидеть нарушение доступа, если вам повезет. Это не вызовет переполнение стека, которое произойдет, только если вы вызовете слишком много функций — обычно через рекурсию.
void f()
{
f(); // <-- stack overflow sure to happen
}
Если вы ищете, чтобы что-то произошло, нет никаких гарантий, что это произойдет. Запись за конец массива — неопределенное поведение. Если система обнаружит, что вы делаете, это почти наверняка приведет вас к краху, но если вы просто перезаписываете память, которая действительно принадлежит вашему процессу, это может не произойти, пока вы не напишете путь до конца.
увидеть Что и где находится стек и куча?
Вы получите переполнение стека довольно быстро, если создадите функцию, которая вызывает себя бесконечно. Каждый вызов функции занимает место в стеке, и вы очень быстро исчерпаете пространство стека!
void f()
{
f();
}
В Visual Studio 2012 этот код даже выдал предупреждение
warning C4717: 'f' : recursive on all control paths, function will cause runtime stack overflow
Эта функция не была оптимизирована в Visual Studio 2012, но, тем не менее, как указывает @MooingDuck, компиляторы могут быть достаточно умными при поиске оптимизаций и потенциальных ошибок в коде.
Контрольным признаком переполнения стека является то, что одна и та же функция повторяется снова и снова в вашем стеке вызовов в вашей программе, когда ваша программа падает! Наверное, лучше посмотреть, как это выглядит сейчас, чтобы вы теперь знали, как это распознать в будущем …