Spec-Zone.ru › C++

std::modf, std::modff, std::modfl

Определено в заголовке <cmath>
(1)
float       modf ( float num, float* iptr );
double      modf ( double num, double* iptr );
long double modf ( long double num, long double* iptr );
(до C++23)
constexpr /* floating-point-type */
            modf ( /* floating-point-type */ num,
                   /* floating-point-type */* iptr );
(с C++23)
float       modff( float num, float* iptr );
(2) (с C++11)
(constexpr с C++23)
long double modfl( long double num, long double* iptr );
(3) (с C++11)
(constexpr с C++23)
Дополнительные перегрузки (с C++11)
Определено в заголовке <cmath>
template< class Integer >
double      modf ( Integer num, double* iptr );
(A) (constexpr с C++23)
1-3) Разделяет заданное значение с плавающей точкой num на целую и дробную части, каждая из которых имеет тот же тип и знак, что и num. Целая часть (в формате с плавающей точкой) сохраняется в объекте, на который указывает iptr. Библиотека предоставляет перегрузки std::modf для всех типов с плавающей точкой без квалификаторов cv в качестве типа параметра num и типа объекта, на который указывает iptr.(с C++23)
A) Дополнительные перегрузки предоставляются для всех целочисленных типов, которые обрабатываются как double. (с C++11)

Параметры

num - значение с плавающей точкой или целое число
iptr - указатель на значение с плавающей точкой для хранения целой части

Возвращаемое значение

При отсутствии ошибок возвращает дробную часть num с тем же знаком, что и num. Целая часть помещается в значение, на которое указывает iptr.

Сумма возвращаемого значения и значения, сохранённого в *iptr, даёт num (с учётом округления).

Обработка ошибок

Данная функция не имеет ошибок, указанных в math_errhandling.

Если реализация поддерживает арифметику с плавающей точкой IEEE (IEC 60559),

  • Если num равно ±0, возвращается ±0, и ±0 сохраняется в *iptr.
  • Если num равно ±∞, возвращается ±0, и ±∞ сохраняется в *iptr.
  • Если num равно NaN, возвращается NaN, и NaN сохраняется в *iptr.
  • Возвращаемое значение точное, текущий режим округления игнорируется.

Примечания

Данная функция ведет себя так, как если бы она была реализована следующим образом:

double modf(double num, double* iptr)
{
#pragma STDC FENV_ACCESS ON
    int save_round = std::fegetround();
    std::fesetround(FE_TOWARDZERO);
    *iptr = std::nearbyint(num);
    std::fesetround(save_round);
    return std::copysign(std::isinf(num) ? 0.0 : num - (*iptr), num);
}

Дополнительные перегрузки не обязаны предоставляться точно как (A). Они должны быть достаточными, чтобы гарантировать, что для их аргумента num целочисленного типа std::modf(num, iptr) имеет тот же эффект, что и std::modf(static_cast<double>(num), iptr).

Пример

Сравнивает различные функции разложения чисел с плавающей точкой:

#include <cmath>
#include <iostream>
#include <limits>
 
int main()
{
    double f = 123.45;
    std::cout << "Given the number " << f << " or " << std::hexfloat
              << f << std::defaultfloat << " in hex,\n";
 
    double f3;
    double f2 = std::modf(f, &f3);
    std::cout << "modf() makes " << f3 << " + " << f2 << '\n';
 
    int i;
    f2 = std::frexp(f, &i);
    std::cout << "frexp() makes " << f2 << " * 2^" << i << '\n';
 
    i = std::ilogb(f);
    std::cout << "logb()/ilogb() make " << f / std::scalbn(1.0, i) << " * "
              << std::numeric_limits<double>::radix
              << "^" << std::ilogb(f) << '\n';
 
    // special values
    f2 = std::modf(-0.0, &f3);
    std::cout << "modf(-0) makes " << f3 << " + " << f2 << '\n';
    f2 = std::modf(-INFINITY, &f3);
    std::cout << "modf(-Inf) makes " << f3 << " + " << f2 << '\n';
}

Возможный вывод:

Given the number 123.45 or 0x1.edccccccccccdp+6 in hex,
modf() makes 123 + 0.45
frexp() makes 0.964453 * 2^7
logb()/ilogb() make 1.92891 * 2^6
modf(-0) makes -0 + -0
modf(-Inf) makes -INF + -0

См. также

trunctruncftruncl
(C++11)(C++11)(C++11)
ближайшее целое число не большее по величине, чем заданное значение
(функция)
Документация C для modf

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/numeric/math/modf

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API