Почему это приводит к 0 и переворачиванию? - PullRequest
1 голос
/ 21 февраля 2012

В настоящее время я пишу свою диссертацию, и я столкнулся с поведением .Net C #, которого я никогда раньше не видел.Я говорю об ошибке в расчете.Я реализовал эту формулу:

1/2 * (Theta i-1 + Theta i) + Sum (Alph k, k = 1, i-1)

Эта формула применяется к 4объекты.Тета во всех объектах объявлена ​​как float со значением 1,5708.Альфа инициализируется с 0 и будет увеличиваться на каждой итерации.

Первая имплментация

    float alpha = 0;
    float value = 0;
    for (int sphereCount = 1; sphereCount < this.spheres.Count; sphereCount++)
    {
        value = (1/2) * (this.spheres[sphereCount - 1].Theta + this.spheres[sphereCount].Theta);
        alpha += value;
    }

При этой версии значение всегда равно 0,0!Поэтому я изменил его на:

Рабочая реализация

    float alpha = 0;
    float value = 0;
    for (int sphereCount = 1; sphereCount < this.spheres.Count; sphereCount++)
    {
        value =(this.spheres[sphereCount - 1].Theta + this.spheres[sphereCount].Theta) * 1/2;
        alpha += value;
    }

Сняв скобки вокруг 1/2 и поместив его в конце расчета, это сработало.

ПОЧЕМУ ЭТО ТАК ???

Кажется, когда вы помещаете 1/2 в скобки, независимо от положения 1/2, результат равен 0,0.Но также, когда я помещаю (1/2) в конце, это приводит к 0.0.У кого-нибудь здесь есть идея, почему?

Ответы [ 6 ]

8 голосов
/ 21 февраля 2012

Это

(1 / 2)

оценивается как 0, потому что это целочисленное деление. Если вы скажете

(1 / 2f)

или

(1 / (float) 2)

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

3 голосов
/ 21 февраля 2012

Если вы напишите 1/2, результат вычисляется с использованием целочисленного деления, которое дает целочисленный результат. Вы можете форсировать деление с плавающей запятой, изменив одно из чисел на число с плавающей запятой, как в 1/2f.

Или вы можете просто написать 0.5, что ИМХО более читабельно, чем 1 / 2.

1 голос
/ 21 февраля 2012

Зачем умножать на 1?Вместо этого:

value =(this.spheres[sphereCount - 1].Theta + this.spheres[sphereCount].Theta) * 1/2; 

почему бы не написать это:

value =(this.spheres[sphereCount - 1].Theta + this.spheres[sphereCount].Theta) / 2; 
0 голосов
/ 21 февраля 2012

Это потому, что 1 и 2 являются целочисленными значениями, а не значениями с плавающей запятой.

Когда вы делите целочисленное значение 1 на целочисленное значение 2, результатом является целочисленное значение 0, а не значение с плавающей запятой 0.5.

Когда вы удалите скобки и измените порядок умножения, другая часть выражения сначала умножится на 1, что неявно преобразует целочисленное значение 1 в значение с плавающей запятой. Затем результат делится на 2, который также будет неявно преобразован в значение с плавающей запятой.

Итак, что вы в итоге делаете:

value = ( (this.spheres[sphereCount - 1].Theta + this.spheres[sphereCount].Theta) * (float)1 ) / (float)2;
0 голосов
/ 21 февраля 2012

Поскольку 1/2 рассматривается как целочисленная арифметика и поэтому округляется до 0.

Удаление скобок меняет порядок операций, и теперь вы делите всю формулу (с плавающей запятой) на два иполучение ответа с плавающей запятой.

0 голосов
/ 21 февраля 2012

Вы должны написать 1,0 / 2 или 0,5 вместо 1 / 2.

1/2 - целочисленное деление, которое приводит к целому числу 0.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...