2015-07-02 3 views
-3

Я пытаюсь упростить дроби в двоичном с этим кодом, который проверяет, если значение четное:Бесконечный цикл при упрощении фракций в двоичном в C

int is_even(floatlet value){ 
    if(value & 1) return 0; 
    return 1; 
} 

И это в то время как петля держит немного смещается, пока значение не будет странный.

while(is_even(numerator) && is_even(denomExp)){ 
    numerator >>= 1; 
    denomExp <<= 1; 
} 

Цикл while продолжает бесконечный цикл. Мне интересно, почему? Мы выполнили тест, и функция is_even работает нормально. Благодаря!

+2

Что такое 'floatlet'? Каковы типы «числитель» и «знаменатель»? – chqrlie

+0

a) 0 четный, и поэтому 0/2 и 0 * 2. b) Вы не потрудились показать объявления или значения числителя и denomExp ... как вы можете ожидать, что кто-либо ответит на ваш вопрос без них? –

+0

Это миниатюрное представление с плавающей запятой числа с плавающей запятой в 8 бит. Числитель и знаменатель - это целые числа. – skaggs

ответ

1

Ваша неправильная петля: вы должны смещать demonExp вправо. Он работает неопределенно для numerator=0 и даже denomExp.

Если numerator и denomExp целые типы, а число только часть numerator/denomExp, вы можете исправить код следующим образом:

while (numerator && is_even(numerator) && is_even(denomExp)) { 
    numerator >>= 1; 
    denomExp >>= 1; 
} 

И наоборот, если denomExp сила 2, по которому можно разделить числитель, вы должны увеличивать его вместо этого, и, возможно, проверить на переполнение:

while (numerator && is_even(numerator)) { 
    numerator >>= 1; 
    denomExp += 1; 
} 

вы должны опубликовать определение типа и семантики, а также полный код в вопросе.

+0

Если denomExp является показателем степени, то они должны декрементировать его, а не сдвигать его. –

+0

@ Cameron Skaggs: Согласен! опубликуйте полное определение типа и полный код! – chqrlie

+0

«вы должны увеличить его» - о, да, вот что я имел в виду. :-) (И я не Cameron Skaggs.) –