2013-03-20 2 views
1

По-видимому, иногда этот код переходит в бесконечный цикл, иногда заканчивается или иногда получает ошибку сегментации в зависимости от машины. Почему поведение непоследовательно?Почему этот код приводит к поведению на разных машинах?

void loop() { 
    int x[512]; 
    int i=0; 
    while (i++ <512) { 
     x[i] = 0; 
    } 
} 
int main() { 
    printf("\nCalling loop -->>\n"); 
    loop(); 
} 
+6

Представьте себе, когда 'i' составляет 511. – GManNickG

+0

, но почему не раздавить иногда? – 4pie0

+0

'' while (i ++ <512) '' эта строка все еще взрывает мне голову. – CppLearner

ответ

5

Потому что вы делаете пост-приращение. Когда i 511 она проходит неравенство, но затем он увеличивает до 512. Назначения x[512] является нарушением прав доступа к памяти, которая может быть или могут быть не (это неопределенная) принадлежит вашей заявке. Как указано в комментариях, на разных платформах наблюдается несколько другое поведение, потому что эта ошибка приводит к так называемому неопределенным поведением. Другими словами, результаты этой (неправильной) операции не определены стандартом C++. А так как разные составители и операционные системы имеют разные основные реализации - вы получаете разные поведение.

+1

На самом деле это, вероятно, переписывает значение 'i' в стеке. –

+0

Правда, наверное. –

+0

@EricJ .: Вероятно, что 'i' выделяется * перед *' x' в памяти или (как я только что видел в своей собственной системе), что между 'x' и' i' существует разрыв. –

1

Если вы вызываете неопределенное поведение (как и вы), вы получаете неопределенное поведение - это означает, что разные компиляторы могут давать разные результаты на одной машине, а разные компиляторы на разных машинах могут давать разные результаты; черт возьми, один компилятор на одной машине может смотреть на фазу луны и решает делать разные вещи в зависимости от этого! И все они правильны, потому что неопределенное поведение - это то, что - undefined.

Если вы получаете бесконечный цикл, то есть вероятность, что &x[512] == &i и когда вы пишете от нуля до x[512] (который является неопределенное поведение), то ноль i и цикл продолжается.

Если он падает, есть вероятность, что x[512] совпадает с некоторой важной управляющей информацией в вызывающем стеке, и, растоптав адрес возврата или указатель кадра, вы полностью испортили систему.

Но, независимо от того, машина и компилятор работают нормально; ваш код является проблемой. Ваша петля должна быть:

while (i < 512) 
    x[i++] = 0; 
Смежные вопросы