Я разрабатываю код, который будет использоваться для управления движением, и у меня возникла проблема с функцией pow. Я использую VS2010 в качестве IDE.
Вот моя проблема: у меня есть:
double p = 100.0000;
double d = 1000.0000;
t1 = pow((p/(8.0000*d),1.00/4.000);
При оценке этой последней функции я не получаю лучшего приближения в результате. Я правильно понимаю 7 десятичных цифр, а все последующие цифры - мусор. Я предполагаю, что функция pow только преобразует любую входную переменную в число с плавающей запятой и выполняет расчет.
- Я прав?
- Если да, то есть ли какой-нибудь код, которым я могу «вдохновиться», чтобы повторно реализовать pow для большей точности?
Изменить: решено.
В конце концов, у меня были проблемы с битами конфигурации FPU, вызванные Direct3D, который использовался платформой OGRE 3D.
Если вы используете OGRE, в графическом интерфейсе конфигурации просто установите «Режим с плавающей запятой = Согласованный».
Если вы используете необработанный Direct3D, при вызове CreateDevice обязательно передайте ему флаг «D3DCREATE_FPU_PRESERVE».
Исходный пост:
Возможно, вы используете библиотеку, которая изменяет точность FPU по умолчанию на одинарную точность. Тогда все операции с плавающей запятой, даже с двойными, будут фактически выполняться как операции с одинарной точностью.
В качестве теста вы можете попробовать вызвать _controlfp( _CW_DEFAULT, 0xffffff ); (необходимо включить ) перед выполнением расчета, чтобы убедиться, что вы получили правильный результат. Это сбросит управляющее слово с плавающей запятой к значениям по умолчанию. Обратите внимание, что при этом будут сброшены и другие настройки, что может вызвать проблемы.
Одной из распространенных библиотек, которая изменяет точность с плавающей запятой, является Direct3D 9 (и, возможно, другие версии): по умолчанию она изменяет FPU на одинарную точность при создании устройства. Если вы его используете, укажите флаг D3DCREATE_FPU_PRESERVE при создании устройства, чтобы предотвратить изменение точности FPU.
pow()
в стандартной библиотеке, поставляемой с вашим компилятором. У glibcpow()
есть прототип со всемиdouble
. Версияfloat
называетсяpowf()
. - person Aftnix   schedule 17.07.2012long double
для большей точности, но, очевидно, Microsoft решила избавиться от этого< /а>. MS C++ имеет аргументыpow
вместоlong double
. - person Fred Foo   schedule 17.07.2012t1
с двойным и исправьте несбалансированную скобку. - person Prashant Kumar   schedule 17.07.2012