Получение дробной части плавания, не используя modf ()

Я столкнулся с этой проблемой, потому что имел переменную-член только с get without set свойством

, что означает ее auto calculated и not stored в качестве столбца в the table

, поэтому его not exist в table schema

, поэтому make sure, что любая переменная-член not auto calculated до have a getter и setter свойства

24
задан knight666 7 April 2010 в 18:27
поделиться

8 ответов

Если я правильно понял ваш вопрос, вам просто нужна часть после десятичной дроби, верно? Вам не нужна дробь (целочисленный числитель и знаменатель)?

Итак, у нас есть какое-то число, скажем 3,14159 , и мы хотим получить только 0,14159 . Предполагая, что наше число хранится в float f; , мы можем сделать это:

f = f-(long)f;

Что, если мы вставим наше число, работает следующим образом:

0.14159 = 3.14159 - 3;

Это удаляет целую часть числа из числа float, оставляя только десятичную часть. Когда вы конвертируете число с плавающей запятой в длинное, оно отбрасывает десятичную часть. Затем, когда вы вычтите это из исходного числа с плавающей запятой, у вас останется только десятичная часть. Здесь нам нужно использовать long из-за размера типа float (8 байтов в большинстве систем). Целое число (всего 4 байта во многих системах) не обязательно достаточно велико, чтобы покрыть тот же диапазон чисел, что и float , но long должно быть.

44
ответ дан 28 November 2019 в 22:36
поделиться
double frac(double val)
{
    return val - trunc(val);
}

// frac(1.0) = 1.0 - 1.0 = 0.0 correct
// frac(-1.0) = -1.0 - -1.0 = 0.0 correct
// frac(1.4) = 1.4 - 1.0 = 0.4 correct
// frac(-1.4) = -1.4 - -1.0 = -0.4 correct

Простой и работы для-ve и +ve

0
ответ дан 28 November 2019 в 22:36
поделиться

Ваш метод предполагает, что в дробной части 16 бит (и, как отмечает Марк Рэнсом, это означает, что вы должны сдвинуть на 16 бит, то есть умножить на на 0x1000). Это могло быть неправдой. Показатель степени определяет, сколько бит находится в дробной части.

Чтобы выразить это в формуле, ваш метод работает, вычисляя (x modf 1.0) как ((x << 16) mod 1 << 16) >> 16 , и это жестко запрограммированные 16, которые должны зависеть от экспоненты - точная замена зависит от вашего формата с плавающей запятой.

0
ответ дан 28 November 2019 в 22:36
поделиться

Я бы порекомендовал посмотреть, как modf реализован в системах, которые вы используете сегодня. Ознакомьтесь с версией uClibc.

http://git.uclibc.org/uClibc/tree/libm/s_modf.c

(По юридическим причинам он, похоже, имеет лицензию BSD, но вы, очевидно, захотите дважды проверить)

Некоторые макросы определены здесь .

5
ответ дан 28 November 2019 в 22:36
поделиться

В ваших константах есть ошибка. Вы в основном пытаетесь сдвинуть число влево на 16 бит, замаскировать все, кроме младших битов, а затем снова сдвинуть вправо на 16 бит. Сдвиг - это то же самое, что умножение на степень 2, но вы не используете степень 2 - вы используете 0xFFFF, который отключен на 1. Замена на 0x10000 заставит формулу работать должным образом.

4
ответ дан 28 November 2019 в 22:36
поделиться

Зачем вообще использовать числа с плавающей запятой для рисования линий? Вы можете просто придерживаться своей версии с фиксированной точкой и вместо этого использовать процедуру рисования линий на основе целых / фиксированных точек - приходит на ум Брезенхэм. Хотя у этой версии нет псевдонима, я знаю, что есть и другие.

Рисование линии Брезенхэма

1
ответ дан 28 November 2019 в 22:36
поделиться

Как я и подозревал, modf не использует никакой арифметики как таковой - это все сдвиги и маски, посмотрите здесь . Разве вы не можете использовать те же идеи на своей платформе?

8
ответ дан 28 November 2019 в 22:36
поделиться

Я не совсем уверен, но думаю, что то, что вы делаете, неправильно, поскольку вы учитываете только мантиссу и полностью забываете показатель степени.

Вам нужно использовать показатель степени, чтобы сдвинуть значение мантиссы, чтобы найти действительную целую часть.

Описание механизма хранения 32-битных чисел с плавающей запятой см. здесь .

3
ответ дан 28 November 2019 в 22:36
поделиться
Другие вопросы по тегам:

Похожие вопросы: