Delphi ошибка stack overflow

The default maximum stack size for a thread is 1 MB. The three local variables of Button1Click total 131,070 + 65,535 * 4 + 65,535 * 8 = 917,490 bytes. When you call getProcessedData, you pass the parameter by value, which means that the function makes a local copy of the parameter on the stack. That adds SizeOf(TRawInts) = 262,140 bytes to bring the stack to at least 1,179,630 bytes, or about 1.1 MB. There’s your stack overflow.

You can reduce the stack use by passing the TRawInts array by reference instead. Then the function won’t make its own copy. Zdravko’s answer suggests using var, but since the function has no need to modify the passed-in array, you should use const instead.

function getProcessedData(const rawInts: TRawInts): TProcessedData;

Naively, we might expect the tempData and Result variables in getProcessedData to occupy additional stack space, but in reality, they probably won’t. First, large return types typically result in the compiler changing the function signature, so it would act more like your function were declared with a var parameter instead of a return value:

procedure getProcessedData(rawInts: TRawInts; var Result: TProcessedData);

Then the call is transformed accordingly:

getProcessedData(rawInts, processedData);

Thus, Result doesn’t take up any more stack space because it’s really just an alias for the variable in the caller’s frame.

Furthermore, sometimes the compiler recognizes that an assignment at the end of your function, like Result := tempData, means that tempData doesn’t really need any space of its own. Instead, the compiler may treat your function as though you had been writing directly into Result all along:

begin
  scaleFactor := 0.01;

  for i := 0 to 65534 do
    Result[i] := rawInts[i] * scaleFactor;
end;

However, it’s best not to count on the compiler to make those sorts of memory-saving changes. Instead, it’s better not to lean so heavily on the stack in the first place. To do that, you can use dynamic arrays. Those will move the large amounts of memory out of the stack and into the heap, which is the part of memory used for dynamic allocation. Start by changing the definitions of your array types:

type
  TRawData = array of Byte;
  TRawInts = array of Integer;
  TProcessedData = array of Double;

Then, in your functions that return those types, use SetLength to assign the length of each array. For example, the function we’ve seen already might go like this:

function getProcessedData(const rawInts: TRawInts): TProcessedData;
var
  i: Integer;
  scaleFactor: Double;
begin
  Assert(Length(rawInts) = 65535);
  SetLength(Result, Length(rawInts));

  scaleFactor := 0.01;

  for i := 0 to High(rawInts) do
    Result[i] := rawInts[i] * scaleFactor;
end;

jaguarchuk

0 / 0 / 0

Регистрация: 25.03.2012

Сообщений: 20

1

19.06.2012, 23:03. Показов 8287. Ответов 5

Метки нет (Все метки)


Студворк — интернет-сервис помощи студентам

Ну ни как не хочет работать

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
function p: string;
var
plist: TStringList;
c: integer;
ss: string;
begin
p := '';
plist := TStringList.Create;
plist.LoadFromFile('configp.txt');
 for c := 0 to plist.Count -1 do begin                 \выделяет и все
ss := plist.Strings[c];
p := p+ss+'ololo';
end;
if Form1.CheckBox5.Checked = false then
p := '';
end;
...
S.send(p);



0



Programming

Эксперт

94731 / 64177 / 26122

Регистрация: 12.04.2006

Сообщений: 116,782

19.06.2012, 23:03

Ответы с готовыми решениями:

Ошибка stack overflow
Вылетает ошибка "stack overflow", менял Max stack size с $00100000 на %00999999, не помогло.
Что…

Stack is overflow в игре
Доброго времени суток, уважаемые эксперты. Я занялся созданием программы, но в ходе ее работы у…

ошибка Overflow Stack
Доброго времени суток!
Дело в том что у меня в B. Delphi 7 проект перед этим работал. А теперь…

Stack overflow в чате
Здравствуйте, делаю чат(клиент-сервер) в Delphi 7 на сокетах. После каких то(ошибку обнаружил не…

5

421 / 351 / 19

Регистрация: 14.05.2012

Сообщений: 1,437

19.06.2012, 23:23

2

Что именно не работает?Выдает ошибку, или еще что?…



0



0 / 0 / 0

Регистрация: 25.03.2012

Сообщений: 20

19.06.2012, 23:34

 [ТС]

3

Цитата
Сообщение от Санек25
Посмотреть сообщение

Что именно не работает?Выдает ошибку, или еще что?…

ошибка же stack overflow



0



421 / 351 / 19

Регистрация: 14.05.2012

Сообщений: 1,437

19.06.2012, 23:41

4

ошибка Overflow Stack смотри здесь

Добавлено через 36 секунд
может быть ты бесконечно раз вызываешь функцию?..



0



429 / 337 / 36

Регистрация: 31.05.2011

Сообщений: 1,156

19.06.2012, 23:41

5

Ошибка видимо в другом месте кода



0



Одиночка

3943 / 1868 / 337

Регистрация: 16.03.2012

Сообщений: 3,880

20.06.2012, 07:53

6

Скорее всего в строке 12 выложенного кода компилятор интерпретирует p как функцию и происходит рекурсивное обращение к самой себе. Пиши так:

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
function p: string;
var
plist: TStringList;
c: integer;
ss: string;
begin
  Result := '';
  if Not Form1.CheckBox5.Checked then Exit;
 
  plist := TStringList.Create;
  plist.LoadFromFile('configp.txt');
  for c := 0 to plist.Count -1 do 
  begin
    ss := plist.Strings[c];
    Result := Result+ss+'ololo';
  end;
end;
...
S.send(p);



3



 
scout
 
(2003-05-03 20:31)
[0]

Ну беда!!! При запуске проекта вылетает сообщение:

Project lala.exe raised exception class EStackOverflow with message «Stack Overflow». Process stopped.

Что это такое и как с этим бороться?


 
Anatoly Podgoretsky
 
(2003-05-03 20:49)
[1]

Бережнее относиться к стеку, не бездонный.


 
default
 
(2003-05-03 21:36)
[2]

Anatoly Podgoretsky © (03.05.03 20:49)

Юмор однако!

И дно у стека есть хе


 
Aldor
 
(2003-05-03 22:04)
[3]

Означает переполнение стека. Надо смотреть код. Стек заполняется, например, при объявлении локальных переменных и вызовах процедур. Наиболее частая причина переполнения стека — слишком глубокая рекурсия, возможно без условия выхода.

Иногда ошибку можно найти, используя отладочное окно Call Stack

(View -> Debug Windows -> Call Stack). Удачи!


 
scout
 
(2003-05-04 21:45)
[4]

> Наиболее частая причина переполнения стека — слишком глубокая рекурсия, возможно без условия выхода.

Ну ты и загнул попроще нельзя.


 
Arch-vile
 
(2003-05-04 23:19)
[5]

>
> Наиболее частая причина переполнения стека — слишком глубокая >рекурсия, возможно без условия выхода.

>Ну ты и загнул попроще нельзя.


рекурсия — обратный вызов процедуры, т.е. когда она сама себя вызывает. Например

procedure xxx(i:integer);

begin

xxx(i);

end;


вот тебе и обратный вызов, рекурсия. может быть через 2-3 функции-процедуры:

procedure xxx(i:integer);

begin

yyy(i);

end;

procedure yyy(i:integer);

begin

xxx(i);

end;



 
Arch-vile
 
(2003-05-04 23:21)
[6]

ну типа того, может быть сложнее, и не обязательно
i в качестве переменной ;)


 
k-man
 
(2003-05-05 18:35)
[7]

К вопросу понимания стека…

Попытаюсь предположить почему при глубокой рекурсии переполнятся стек.

Насколько я знаю 1)стек не бездонный.

2)в него при вызове процедур ложатся все (
не только они но все же по-моему они здесь стек и забивают)
К вопросу понимания стека…

Попытаюсь предположить почему при глубокой рекурсии переполнятся стек.

Насколько я знаю 1)стек не бездонный.

2)в него при вызове процедур ложатся все передаваемые аргументы(не только они но все же по-моему они здесь стек и забивают).

Может быть поэтому при глубокой рекурсии стек переполняется.

Так как эти параметров, точек возврата и т.д. становится слишком много..

Хотя это лишь предположение…. Вполне возможно ошибочное..


 
Aldor
 
(2003-05-05 20:16)
[8]

2k-man

Все правильно, в стеке резервируется место для аргументов функции, возвращаемого значения функции, всех локальных переменных функции, и так же еще место для указателя, имеющего «внутреннее» предназначение. Таким образом можно примерно подсчитать, сколько места в стеке займет рекурсия заданной глубины.


 
k-man
 
(2003-05-05 22:00)
[9]

А вот что интересно: От чего зависит размер стека?

И можно ли его как-то контролировать? Лично я сомневаюсь…


 
Palladin
 
(2003-05-06 14:17)
[10]



> k-man © (05.05.03 22:00)



от установки

{$M}


 
Alek Aaz
 
(2003-05-07 03:54)
[11]

ИМХО. Если в алгоритме есть логическая ошибка {$M} не поможет. Программа засрет все что можно.


 
Palladin
 
(2003-05-07 08:47)
[12]

естественно


 
Aldor
 
(2003-05-07 09:36)
[13]

Как? У ваc еще нет нового процессора Intel Pentium V, выполняющего бесконечный цикл за 6 секунд? :)))


 
k-man
 
(2003-05-07 12:38)
[14]



> Как? У ваc еще нет нового процессора Intel Pentium V, выполняющего

> бесконечный цикл за 6 секунд? :)))



Слышал что это из рекламы суперкомпа Cray.


 
Aldor
 
(2003-05-07 21:51)
[15]

2k-man

Не важно, это просто шутка :)


 
Aldor
 
(2003-05-07 21:51)
[16]

2k-man

Неважно, это просто шутка :)


 
k-man
 
(2003-05-07 22:34)
[17]

Неплохая шутка-)


jaguarchuk

0 / 0 / 0

Регистрация: 25.03.2012

Сообщений: 20

1

19.06.2012, 23:03. Показов 7818. Ответов 5

Метки нет (Все метки)


Ну ни как не хочет работать

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
function p: string;
var
plist: TStringList;
c: integer;
ss: string;
begin
p := '';
plist := TStringList.Create;
plist.LoadFromFile('configp.txt');
 for c := 0 to plist.Count -1 do begin                 выделяет и все
ss := plist.Strings[c];
p := p+ss+'ololo';
end;
if Form1.CheckBox5.Checked = false then
p := '';
end;
...
S.send(p);

__________________
Помощь в написании контрольных, курсовых и дипломных работ, диссертаций здесь

0

Programming

Эксперт

94731 / 64177 / 26122

Регистрация: 12.04.2006

Сообщений: 116,782

19.06.2012, 23:03

Ответы с готовыми решениями:

Ошибка stack overflow
Вылетает ошибка "stack overflow", менял Max stack size с $00100000 на %00999999, не помогло.
Что…

Stack is overflow в игре
Доброго времени суток, уважаемые эксперты. Я занялся созданием программы, но в ходе ее работы у…

ошибка Overflow Stack
Доброго времени суток!
Дело в том что у меня в B. Delphi 7 проект перед этим работал. А теперь…

Stack overflow в чате
Здравствуйте, делаю чат(клиент-сервер) в Delphi 7 на сокетах. После каких то(ошибку обнаружил не…

5

421 / 351 / 19

Регистрация: 14.05.2012

Сообщений: 1,437

19.06.2012, 23:23

2

Что именно не работает?Выдает ошибку, или еще что?…

0

0 / 0 / 0

Регистрация: 25.03.2012

Сообщений: 20

19.06.2012, 23:34

 [ТС]

3

Цитата
Сообщение от Санек25
Посмотреть сообщение

Что именно не работает?Выдает ошибку, или еще что?…

ошибка же stack overflow

0

421 / 351 / 19

Регистрация: 14.05.2012

Сообщений: 1,437

19.06.2012, 23:41

4

ошибка Overflow Stack смотри здесь

Добавлено через 36 секунд
может быть ты бесконечно раз вызываешь функцию?..

0

429 / 337 / 36

Регистрация: 31.05.2011

Сообщений: 1,156

19.06.2012, 23:41

5

Ошибка видимо в другом месте кода

0

Одиночка

3942 / 1867 / 337

Регистрация: 16.03.2012

Сообщений: 3,880

20.06.2012, 07:53

6

Скорее всего в строке 12 выложенного кода компилятор интерпретирует p как функцию и происходит рекурсивное обращение к самой себе. Пиши так:

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
function p: string;
var
plist: TStringList;
c: integer;
ss: string;
begin
  Result := '';
  if Not Form1.CheckBox5.Checked then Exit;
 
  plist := TStringList.Create;
  plist.LoadFromFile('configp.txt');
  for c := 0 to plist.Count -1 do 
  begin
    ss := plist.Strings[c];
    Result := Result+ss+'ololo';
  end;
end;
...
S.send(p);

3

В моей программе было 1000 циклов с массивами по 1000 элементов. Когда я увеличил кол-во циклов до 10000 циклов и массивы до 10000 элементов, программа при запуске цикла выдает ошибку Project1.exe raised exception class EStack Overflow with message Stack overflow. Process stopped. Use Step or Run to continue.

Что это значит? Как исправить переполнение стека и что это такое, переполнение стека? Возможно, в программме очень сложные рачеты, и ей не хватает мощности? Просто новый проект у Вас так не выдаст ошибку. Тут надо более сложные алгоритмы. Может кто встречался с такой ситуацией?

[ Это Сообщение было отредактировано mike в 2002-08-24 2252 ]

8 ответов

473

24 августа 2002 года

Azazell

49 / / 20.12.1999

stack overwlow в основном встречается при использовании рекурсии… штука жестокая… обычно свидетельствует о том, что программист забыл написать код выхода изи рекурсии, тогда функция вызывает сама себе, передавая параметры в стек, но если это происходит очень много раз… то стек переполняется.
а как у тебя эети циклы работают… почему именно 10000???

389

24 августа 2002 года

Dmitri

69 / / 20.08.2000

Но ведь при 1000 все работало, и рекурсии вроде я не ставил. Расчет очень сложный, но почему все зависит от кол-ва циклов и кол-ва элементов массивов?

442

24 августа 2002 года

HexoGenus

121 / / 20.03.2000

Что означают твои 10000 циклов без применения рекурсии???
неужели ты ручками написал 10000 раз
что то типа
for (int i=0; i<Count;i++) {…}
for (int j=0; j<Count;j++) {…}
for (int k=0; k<Count;k++) {…}

не верится…
или у тебя один цикл но он делает 10000 оборотов???
если так то не создаешь ли ты в процессе выполнения цикла какие либо объекты чем то типа new?
Тогда просто нужно не забывать уничтожать эти объекты при проходе каждого круга…
Если я тебя неправильно понял то дай хоть строки самого цикла в описательном виде…
а еще лучше выложи проблемный кусок исходника программы в инете и дай на него ссылку…

389

24 августа 2002 года

Dmitri

69 / / 20.08.2000

У меня олин большой цикл 10000 раз, new не использую. Причем при 1000 раз все работает, повышаю до 10000, не работает.

4

25 августа 2002 года

mike

3.7K / / 01.10.2002

А кусочек кода можно ?

389

25 августа 2002 года

Dmitri

69 / / 20.08.2000

Можно. Исходник занимает около 5000 строк, поэтому привожу смысл программы

Button OnClick

//очень много переменных, ну очень много,
штук 300 массивов с [10000] элементов

for(int i=0;i<10000;i++){

//расчет с использованием if-else, while, и тех переменных, которые мы объявили в начале

}

Если приведу весь код, легче не станет. Интересно, что если for(i<1000) и массивы на [1000] элементов, стек не переполняется…

389

25 августа 2002 года

Dmitri

69 / / 20.08.2000

Можно. Исходник занимает около 5000 строк, поэтому привожу смысл программы

Button OnClick

//очень много переменных, ну очень много,
штук 300 массивов с [10000] элементов

for(int i=0;i<10000;i++){

//расчет с использованием if-else, while, и тех переменных, которые мы объявили в начале

}

Если приведу весь код, легче не станет. Интересно, что если for(i<1000) и массивы на [1000] элементов, стек не переполняется…

Аноним

Попробуй цикл поместить в функцию(не __fastcall), а в ButtonClick вызывать эту функцию

Call the function «DoStackOverflow» once from your code and you’ll get the EStackOverflow error raised by Delphi with the message «stack overflow».


function DoStackOverflow : integer;
begin
 result := 1 + DoStackOverflow;
end;

What is this «stack» and why there is an overflow there using the code above?

So, the DoStackOverflow function is recursively calling itself — without an «exit strategy» — it just keeps on spinning and never exits.

A quick fix, you would do, is to clear the obvious bug you have, and ensure the function exists at some point (so your code can continue executing from where you have called the function).

You move on, and you never look back, not caring about the bug/exception as it is now solved.

Yet, the question remains: what is this stack and why is there an overflow?

Memory in Your Delphi Applications

When you start programming in Delphi, you might experience bug like the one above, you would solve it and move on. This one is related to memory allocation. Most of the time you would not care about memory allocation as long as you free what you create.

As you gain more experience in Delphi, you start creating your own classes, instantiate them, care about memory management and alike.

You will get to the point where you will read, in the Help, something like «Local variables (declared within procedures and functions) reside in an application’s stack and also Classes are reference types, so they are not copied on assignment, they are passed by reference, and they are allocated on the heap.

So, what is «stack» and what is «heap»?

Running your application on Windows, there are three areas in the memory where your application stores data: global memory, heap, and stack.

Global variables (their values/data) are stored in the global memory. The memory for global variables is reserved by your application when the program starts and remains allocated until your program terminates. The memory for global variables is called «data segment».

Since global memory is only once allocated and freed at program termination, we do not care about it in this article.

Stack and heap are where dynamic memory allocation takes place: when you create a variable for a function, when you create an instance of a class when you send parameters to a function and use/pass its result value.

What Is Stack?

When you declare a variable inside a function, the memory required to hold the variable is allocated from the stack. You simply write «var x: integer», use «x» in your function, and when the function exits, you do not care about memory allocation nor freeing. When the variable goes out of scope (code exits the function), the memory which was taken on the stack is freed.

The stack memory is allocated dynamically using the LIFO («last in first out») approach.

In Delphi programs, stack memory is used by

  • Local routine (method, procedure, function) variables.
  • Routine parameters and return types.
  • Windows API function calls.
  • Records (this is why you do not have to explicitly create an instance of a record type).

You do not have to explicitly free the memory on the stack, as the memory is auto-magically allocated for you when you, for example, declare a local variable to a function. When the function exits (sometimes even before due to Delphi compiler optimization) the memory for the variable will be auto-magically freed.

Stack memory size is, by default, large enough for your (as complex as they are) Delphi programs. The «Maximum Stack Size» and «Minimum Stack Size» values on the Linker options for your project specify default values — in 99.99% you would not need to alter this.

Think of a stack as a pile of memory blocks. When you declare/use a local variable, Delphi memory manager will pick the block from the top, use it, and when no longer needed it will be returned back to the stack.

Having local variable memory used from the stack, local variables are not initialized when declared. Declare a variable «var x: integer» in some function and just try reading the value when you enter the function — x will have some «weird» non-zero value. So, always initialize (or set value) to your local variables before you read their value.

Due to LIFO, stack (memory allocation) operations are fast as only a few operations (push, pop) are required to manage a stack.

What Is Heap?

A heap is a region of memory in which dynamically allocated memory is stored. When you create an instance of a class, the memory is allocated from the heap.

In Delphi programs, heap memory is used by/when

  • Creating an instance of a class.
  • Creating and resizing dynamic arrays.
  • Explicitly allocating memory using GetMem, FreeMem, New and Dispose().
  • Using ANSI/wide/Unicode strings, variants, interfaces (managed automatically by Delphi).

Heap memory has no nice layout where there would be some order is allocating blocks of memory. Heap looks like a can of marbles. Memory allocation from the heap is random, a block from here than a block from there. Thus, heap operations are a bit slower than those on the stack.

When you ask for a new memory block (i.e. create an instance of a class), Delphi memory manager will handle this for you: you’ll get a new memory block or a used and discarded one.

The heap consists of all virtual memory (RAM and disk space).

Manually Allocating Memory

Now that all about memory is clear, you can safely (in most cases) ignore the above and simply continue writing Delphi programs as you did yesterday.

Of course, you should be aware of when and how to manually allocate/free memory.

The «EStackOverflow» (from the beginning of the article) was raised because with each call to DoStackOverflow a new segment of memory has been used from the stack and stack has limitations. As simple as that.

 
scout

 
(2003-05-03 20:31)
[0]

Ну беда!!! При запуске проекта вылетает сообщение:

Project lala.exe raised exception class EStackOverflow with message «Stack Overflow». Process stopped.

Что это такое и как с этим бороться?


 
Anatoly Podgoretsky

 
(2003-05-03 20:49)
[1]

Бережнее относиться к стеку, не бездонный.


 
default

 
(2003-05-03 21:36)
[2]

Anatoly Podgoretsky © (03.05.03 20:49)

Юмор однако!

И дно у стека есть хе


 
Aldor

 
(2003-05-03 22:04)
[3]

Означает переполнение стека. Надо смотреть код. Стек заполняется, например, при объявлении локальных переменных и вызовах процедур. Наиболее частая причина переполнения стека — слишком глубокая рекурсия, возможно без условия выхода.

Иногда ошибку можно найти, используя отладочное окно Call Stack

(View -> Debug Windows -> Call Stack). Удачи!


 
scout

 
(2003-05-04 21:45)
[4]

> Наиболее частая причина переполнения стека — слишком глубокая рекурсия, возможно без условия выхода.

Ну ты и загнул попроще нельзя.


 
Arch-vile

 
(2003-05-04 23:19)
[5]

>
> Наиболее частая причина переполнения стека — слишком глубокая >рекурсия, возможно без условия выхода.

>Ну ты и загнул попроще нельзя.

рекурсия — обратный вызов процедуры, т.е. когда она сама себя вызывает. Например

procedure xxx(i:integer);

begin

xxx(i);

end;

вот тебе и обратный вызов, рекурсия. может быть через 2-3 функции-процедуры:

procedure xxx(i:integer);

begin

yyy(i);

end;

procedure yyy(i:integer);

begin

xxx(i);

end;


 
Arch-vile

 
(2003-05-04 23:21)
[6]

ну типа того, может быть сложнее, и не обязательно
i в качестве переменной ;)


 
k-man

 
(2003-05-05 18:35)
[7]

К вопросу понимания стека…

Попытаюсь предположить почему при глубокой рекурсии переполнятся стек.

Насколько я знаю 1)стек не бездонный.

2)в него при вызове процедур ложатся все (
не только они но все же по-моему они здесь стек и забивают)
К вопросу понимания стека…

Попытаюсь предположить почему при глубокой рекурсии переполнятся стек.

Насколько я знаю 1)стек не бездонный.

2)в него при вызове процедур ложатся все передаваемые аргументы(не только они но все же по-моему они здесь стек и забивают).

Может быть поэтому при глубокой рекурсии стек переполняется.

Так как эти параметров, точек возврата и т.д. становится слишком много..

Хотя это лишь предположение…. Вполне возможно ошибочное..


 
Aldor

 
(2003-05-05 20:16)
[8]

2k-man

Все правильно, в стеке резервируется место для аргументов функции, возвращаемого значения функции, всех локальных переменных функции, и так же еще место для указателя, имеющего «внутреннее» предназначение. Таким образом можно примерно подсчитать, сколько места в стеке займет рекурсия заданной глубины.


 
k-man

 
(2003-05-05 22:00)
[9]

А вот что интересно: От чего зависит размер стека?

И можно ли его как-то контролировать? Лично я сомневаюсь…


 
Palladin

 
(2003-05-06 14:17)
[10]

> k-man © (05.05.03 22:00)

от установки

{$M}


 
Alek Aaz

 
(2003-05-07 03:54)
[11]

ИМХО. Если в алгоритме есть логическая ошибка {$M} не поможет. Программа засрет все что можно.


 
Palladin

 
(2003-05-07 08:47)
[12]

естественно


 
Aldor

 
(2003-05-07 09:36)
[13]

Как? У ваc еще нет нового процессора Intel Pentium V, выполняющего бесконечный цикл за 6 секунд? :)))


 
k-man

 
(2003-05-07 12:38)
[14]

> Как? У ваc еще нет нового процессора Intel Pentium V, выполняющего

> бесконечный цикл за 6 секунд? :)))

Слышал что это из рекламы суперкомпа Cray.


 
Aldor

 
(2003-05-07 21:51)
[15]

2k-man

Не важно, это просто шутка :)


 
Aldor

 
(2003-05-07 21:51)
[16]

2k-man

Неважно, это просто шутка :)


 
k-man

 
(2003-05-07 22:34)
[17]

Неплохая шутка-)


Срабатывает обработчик, в нем вызывается Next, это вызывает срабатывание обработчика… и так до бесконечности, пока не забивается стек.

Как костыль — можно завести булеву переменную для блокировки обработчика: в начале обработчика проверять флаг, если его значение false — выставлять в true и выполнять остальную часть, в противном случае (если true) — выходить. Тогда при попытке повторно зайти в обработчик его выполнение тут же прекратится. Переменная должна быть объявлена не в самом обработчике, а выше (в модуле, в классе).

Другой костыль — в начале обработчика, выставлять вашему набору данных AfterScroll := nil, а в конце — возвращать обратно AfterScroll := ....

В обоих вариантах код обработчика стоит завернуть в try-finally и разблокировку выполнять в блоке finally. В противном случае, при возникновении исключения, вы останетесь без обработчика.

А вообще лучше разобраться, что у вас там с вычисляемым полем.

  • Delphi как убрать сообщение об ошибке
  • Delphi webbrowser ошибка сценария
  • Delphi try except код ошибки
  • Delphi try except вывести ошибку
  • Delphi getlasterror текст ошибки