2016-10-07 5 views
-4
#include <stdio.h> 
int test1(int x, int n){ 
    int times=31/n; 
    return ((1-(1<<(n*times)))/(1-(1<<n))); 
} 

Я делаю расчет, где 1 < = п < = 32исключение с плавающей запятой в коде C

Это только работает, когда 1 < = п < = 31, как я могу изменить его для п = 32 ? Как я могу проверить его п = 32 случай, в Xcode, он запускает отладчик и показывает поток 1 exc_arithmetic (код = exc_i386_div ....
Спасибо заранее.

+1

В этом коде нет * ничего *, которое можно назвать «с плавающей запятой» или «исключением» ... –

+1

Как мы можем сказать вам, как заставить его «работать», если вы не сообщите нам, что это такое делать? – kaylum

+1

Что должно быть ** целочисленным ** результатом '31/32'? –

ответ

1

Существует неплохой шанс, что когда вы делаете 1 << 32, он обрабатывается как 1 << 0 (и, поскольку вы вызываете неопределенное поведение, это нормально), а затем вы получаете «исключение с плавающей точкой», потому что вы делаете целое число «деление на ноль». В наши дни это самая распространенная причина для исключения. Если вы делали арифметику с плавающей запятой, вы получили бы бесконечность, возвращенную (беззвучно) для деления на ноль.

0

Я только выяснил, как я могу это исправить. Проблема в том, что проблема 1<<32 case (что я попытается подъязычная).

Я изменил 1 << n на (1 << (n-1))*2, еще один способ применения математики.

return ((1-(1<<(n*times)))/(1- (1<<(n-1))*2 )); 
+0

Если ваш тип 'int' - это 32-разрядный тип, вы все равно вызываете неопределенное поведение. И если он был длиннее 32 бит, вы бы не получили ошибку в первую очередь. Можете ли вы объяснить, что ваш расчет должен оценивать? –

+0

@JonathanLeffler, то, что я делал, это получить 32-битные int и число n в качестве входов, а выход должен быть заполнен повторением n бит ввода. Например, если входной сигнал равен 1 и 2. (повторяющийся шаблон равен 01), выход должен быть 0x55555555. если вход 0x12345678, 32, выход будет только 0x12345678. Я получаю вывод, выясняя, что могу рассчитать сумму последовательных рядов. и тот, который я прошу, является его частью. – Jack

0

Некоторые современные реализации для 2's-комплемент платформ генерировать «исключение с плавающей запятой» в ответ на целочисленное переполнение деления, которое происходит в следующем коде

int a = INT_MIN; 
int b = -1; 
int c = a/b; 

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

Очевидно, ваше выражение сталкивается с такой же проблемой, как и практическое проявление неопределенного поведения на платформе, вызванное «перевершением» целого числа.

P.S. Как отмечает @Jonathan Leffler, целочисленное деление на ноль также генерирует «исключение с плавающей запятой» в GCC, что, вероятно, еще более вероятно произойдет в вашем случае.

Смежные вопросы