До какой длины я должен go, чтобы избежать повышения FE_INEXACT в коде библиотеки? - PullRequest
1 голос
/ 03 августа 2020

Я создаю библиотеку в C, которая содержит общие структуры данных, вспомогательные функции и т. Д. c. который предназначен для общего использования. Внутри я реализовал массив Dynami c и выбрал золотое сечение в качестве фактора роста по причине, объясненной здесь . Однако это обязательно включает в себя умножение чисел с плавающей запятой, что может вызвать увеличение FE_INEXACT, если они имеют большие значения.

Когда я реализовал это, у меня сложилось впечатление, что, поскольку библиотека предназначена для при общем использовании следует избегать исключений с плавающей запятой, если это вообще возможно. Сначала я попробовал что-то вроде

fenv_t fenv;
feholdexcept(&fenv);
// expand dynamic array
feclearexcept(FE_INEXACT);
feupdateenv(&fenv);

, но это потребовало таких огромных временных затрат, что оно того не стоило.

В конце концов, я пришел к решению, которое имело незначительные временные затраты. . Хотя это не исключало полностью FE_INEXACT, это делало его маловероятным. А именно,

size_t newCapacity = nearbyint((double)(float)PHI * capacity);

Это повысит FE_INEXACT только в том случае, если текущая емкость чрезвычайно велика, по крайней мере, для компиляторов, которые придерживаются стандартов IEEE 754.

Я начинаю задаваться вопросом, может ли мои усилия пошли на решение относительно несложной проблемы. Для библиотечного кода разумно ли ожидать, что пользователь обработает повышение FE_INEXACT, когда это необходимо, или этого следует избегать в библиотеке? В последнем случае насколько важна проблема по сравнению с другими факторами, такими как эффективность?

1 Ответ

4 голосов
/ 03 августа 2020

До какой длины я должен go ...

Ни одного. Почти никто не использует fenv.h, компиляторы даже не полностью поддерживают его (они делают преобразования, которые ошибочно игнорируют или изменяют среду с плавающей запятой), и если кто-то, вызывающий ваш код, использует его, вполне разумно потребовать от них сохранить / восстановить исключение сообщать о звонках в вашу библиотеку. Более того, в большинстве случаев, если вы выполняете операцию, которая вызывает FE_INEXACT, это именно потому, что результат, который вы собираетесь вернуть, неточен, и поэтому семантически целесообразно повышать его.

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