Bibliothèque standard C++<numbers>

Avant C++20, nous écrivions généralement les constantes mathématiques comme ceci :

const double PI = 3.14159265358979323846;

Le problème est très évident :La précision était définie de manière arbitraire, incohérente, source d'erreurs et non sûre du point de vue des types./p>

C++20 a officiellement introduit#include <numbers>, fournissant un ensemble normalisé de constantes mathématiques, avec une précision et une exactitude de type garanties par le compilateur.

std::numbersIl s'agit d'un module de la bibliothèque standard introduit en C++20, principalement utilisé pour fournir un ensemble de constantes mathématiques couramment utilisées, servant de référentiel standard de constantes mathématiques et physiques.

std::numbersSitué à<numbers>dans le fichier d'en-tête, et contient de nombreuses constantes mathématiques, couvrant des constantes courantes telles que pi, la base des logarithmes népériens, le nombre d'or, etc.

L'utilisation de ces constantes en C++ peut améliorer la lisibilité, la précision et l'efficacité du code, en évitant les définitions répétées et la saisie manuelle des valeurs de constantes.

std::numbersAvantages par rapport à l'écriture traditionnelle :

Dimension Approche traditionnelle <numbers>
Precision Ad hoc Haute précision standard
Type Fixe Correspondance automatique
Lisibilité Moyenne Sémantique claire
Constante à la compilation Pas nécessairement Certainement
Normalisation Médiocre Niveau bibliothèque standard

Constantes contenues dans le module std::numbers

L'espace de noms std::numbers contient les membres suivants :

template<floating_point T> inline constexpr T e_v<T> // 自然常数e
template<floating_point T> inline constexpr T log2e_v<T> // log2e
template<floating_point T> inline constexpr T log10e_v<T> // log10e
template<floating_point T> inline constexpr T pi_v<T> // 圆周率π
template<floating_point T> inline constexpr T inv_pi_v<T> // 1/π
template<floating_point T> inline constexpr T inv_sqrtpi_v<T> //1/根号π
template<floating_point T> inline constexpr T ln2_v<T> // ln2
template<floating_point T> inline constexpr T ln10_v<T> // ln10
template<floating_point T> inline constexpr T sqrt2_v<T> //根号2
template<floating_point T> inline constexpr T sqrt3_v<T> //根号3
template<floating_point T> inline constexpr T inv_sqrt3_v<T> // 1/根号3
template<floating_point T> inline constexpr T egamma_v<T> // 欧拉常数γ
template<floating_point T> inline constexpr T phi_v<T> // 黄金分割比Φ
inline constexpr double e = e_v<double>
inline constexpr double log2e = log2e_v<double>
inline constexpr double log10e = log10e_v<double>
inline constexpr double pi = pi_v<double>
inline constexpr double inv_pi = pi_v<double>
inline constexpr double inv_sqrtpi = pi_v<double>
inline constexpr double ln2 = ln2_v<double>
inline constexpr double ln10 = ln10_v<double>
inline constexpr double sqrt2 = sqrt2_v<double>
inline constexpr double sqrt3 = sqrt3_v<double>
inline constexpr double inv_sqrt3 = sqrt3_v<double>
inline constexpr double egamma = egamma_v<double>
inline constexpr double phi = phi_v<double>

Voici une liste des constantes contenues dans std::numbers :

Nom de constante/modèleDescriptionExemples de valeurs (approximatives)
e_vConstante mathématique e (base des logarithmes naturels)2.718281828459045
log2e_vLogarithme de e en base 2 (log₂(e))1.4426950408889634
log10e_vLogarithme de e en base 10 (log₁₀(e))0.4342944819032518
pi_vConstante mathématique π (pi)3.141592653589793
inv_pi_v1/π (l'inverse de π)0.318309886183121
inv_sqrtpi_v1/√π (inverse de la racine carrée de π)0.5641895835477563
ln2_vLogarithme népérien de 2 (ln(2))0.6931471805599453
ln10_vLogarithme népérien de 10 (ln(10))2.302585092994046
sqrt2_v√2 (racine carrée de 2)1.4142135623730951
sqrt3_v√3 (racine carrée de 3)1.7320508075688772
inv_sqrt3_v1/√3 (inverse de la racine carrée de 3)0.5773502691896257
egamma_vConstante d'Euler-Mascheroni γ0.5772156649015329
phi_vNombre d'or Φ ((1 + √5) / 2)1.618033988749895
eConstante e (équivalente àe_v<double>)2.718281828459045
log2eConstante log₂(e) (équivalente àlog2e_v<double>)1.4426950408889634
log10eConstante log₁₀(e) (équivalente àlog10e_v<double>)0.4342944819032518
piConstante π (équivalente àpi_v<double>)3.141592653589793
inv_piConstante 1/π (équivalente àinv_pi_v<double>)0.318309886183121
inv_sqrtpiConstante 1/√π (équivalente àinv_sqrtpi_v<double>)0.5641895835477563
ln2Constante ln(2) (équivalente àln2_v<double>)0.6931471805599453
ln10Constante ln(10) (équivalente àln10_v<double>)2.302585092994046
sqrt2Constante √2 (équivalente àsqrt2_v<double>)1.4142135623730951
sqrt3Constante √3 (équivalente àsqrt3_v<double>)1.7320508075688772
inv_sqrt3Constante 1/√3 (équivalente àinv_sqrt3_v<double>)0.5773502691896257
egammaConstante γ (constante d’Euler–Mascheroni) (équivalente àegamma_v<double>)0.5772156649015329
phiConstante du nombre d’or Φ (équivalente àphi_v<double>)1.618033988749895

Ces constantes et modèles de variables couvrent des constantes mathématiques couramment utilisées telles que pi, la base du logarithme népérien, le nombre d'or, et fournissent des options de précision via des modèles de variables de différents types, tels que float, double et long double.

Exemple

#include <iostream>
#include <iomanip>
#include <numbers>
#include <cmath> // pour les fonctions mathématiques standard sin, cos, log, etc.

using namespace std;

int main()
{
    // Utiliser les constantes de type double par défaut
    cout << fixed << setprecision(15); // Définir toutes les sorties sur 15 décimales

    // Afficher la valeur de π (pi)
    cout << "La valeur de pi est : " << numbers::pi << endl;

    // Afficher la valeur de e (base du logarithme népérien)
    cout << "La valeur de la constante naturelle e est : " << numbers::e << endl;

    // Afficher la valeur de la racine carrée de 2 (sqrt2)
    cout << "La valeur de la racine carrée de 2 (sqrt2) est : " << numbers::sqrt2 << endl;

    // Afficher la valeur de la racine carrée de 3 (sqrt3)
    cout << "La valeur de la racine carrée de 3 (sqrt3) est : " << numbers::sqrt3 << endl;

    // Afficher la valeur du nombre d'or phi
    cout << "La valeur du nombre d'or phi est : " << numbers::phi << endl;

    // Afficher la valeur de la constante d'Euler-Mascheroni egamma
    cout << "La valeur de la constante d'Euler-Mascheroni egamma est : " << numbers::egamma << endl;

    // Afficher la valeur de 1/π (inv_pi)
    cout << "La valeur de 1/π (inv_pi) est : " << numbers::inv_pi << endl;

    // Afficher la valeur de 1/√π (inv_sqrtpi)
    cout << "La valeur de 1/√π (inv_sqrtpi) est : " << numbers::inv_sqrtpi << endl;

    // Afficher la valeur de log2e, le logarithme en base 2 de e
    cout << "La valeur de log2e, le logarithme en base 2 de e, est : " << numbers::log2e << endl;

    // Afficher la valeur de log10e, le logarithme en base 10 de e
    cout << "La valeur de log10e, le logarithme en base 10 de e, est : " << numbers::log10e << endl;

    // Afficher la valeur de sin(π/2)
    cout << "La valeur de sin(π/2) est : " << sin(numbers::pi / 2) << endl;

    // Afficher la valeur de cos(π)
    cout << "La valeur de cos(π) est : " << cos(numbers::pi) << endl;

    // Afficher la valeur de ln(e)
    cout << "La valeur de ln(e) est : " << log(numbers::e) << endl;

    // Démontrer l'utilisation de différents types de données
    float pi_f = numbers::pi_v<float>;  // Utiliser pi de type float
    cout << "\nUtiliser pi de type float : " << setprecision(7) << pi_f << endl; // Afficher 7 décimales
   
    long double pi_ld = numbers::pi_v<long double>;  // Utiliser pi de type long double
    cout << "Utiliser pi de type long double : " << setprecision(21) << pi_ld << endl; // Afficher 21 décimales

    // Calculer des valeurs avec différentes précisions
    cout << "\n"sin(π/2) avec double : " << sin(numbers::pi / 2) << endl;
    cout << "sin(π/2) avec float : " << sin(static_cast<float>(numbers::pi) / 2) << endl;
    cout << "sin(π/2) avec long double : " << sin(static_cast<long double>(numbers::pi) / 2) << endl;

    return 0;
}

Analyse du code :

Sortie formatée :

  • Utilisationfixedetsetprecision()pour garantir un nombre fixe de chiffres après le point décimal dans la sortie. Ici, 15 décimales sont affichées par défaut, mais une précision différente peut également être définie pour chaque type de données différent.

Calculer les fonctions mathématiques courantes :

  • calculésin(π/2)、cos(π)etln(e)et d'autres fonctions mathématiques courantes, et utilisercmathfonctions dans (par exemplesin、cosetlog) pour démontrer comment utiliser les constantes mathématiques.

Précision pour différents types de données :

  • Utilisationnumbers::pi_v<float>etnumbers::pi_v<long double>pour démontrer différents types de constantes. Pourfloatetlong double, vous pouvez afficher avec une précision différente.

Calculs utilisant différents types :

  • Lors du calculsinlorsque ..., cela montre comment effectuer des calculs en utilisant des types de précision différente, illustrantfloat、doubleetlong doubleles différences sous la même expression mathématique.

Sortie :

圆周率 pi 的值是: 3.141592653589793
自然常数 e 的值是: 2.718281828459045
根号2 (sqrt2) 的值是: 1.414213562373095
根号3 (sqrt3) 的值是: 1.732050807568877
黄金比例 phi 的值是: 1.618033988749895
欧拉-马歇罗尼常数 egamma 的值是: 0.5772156649015329
1/π (inv_pi) 的值是: 0.318309886183121
1/√π (inv_sqrtpi) 的值是: 0.5641895835477563
以 2 为底的 e 的对数 log2e 的值是: 1.4426950408889634
以 10 为底的 e 的对数 log10e 的值是: 0.4342944819032518
sin(π/2) 的值是: 1
cos(π) 的值是: -1
ln(e) 的值是: 1

使用 float 类型的 pi: 3.1415927
使用 long double 类型的 pi: 3.141592653589793238462643
sin(π/2) 使用 double: 1
sin(π/2) 使用 float: 1
sin(π/2) 使用 long double: 1

Exemples d’utilisation

Les exemples suivants couvrent<numbers>Les constantes les plus couramment utilisées ; le code peut être compilé et exécuté directement. N'oubliez pas d'ajouter un paramètre standard-std=c++20:

g++ -std=c++20 main.cpp -o main

Exemple 1 : Utilisation de base

Calcul de l'aire / de la circonférence d'un cercle à l'aide de π :

Exemple

#include <iostream>
#include <numbers> // inclut les constantes mathématiques
#include <cmath> // inclut les fonctions mathématiques telles que pow

using namespace std;
using namespace std::numbers;  // Simplifier les appels aux constantes (facultatif)

int main() {
    // Le rayon du cercle
    double r = 5.0;

    // 1. Calculer la circonférence du cercle : 2 * π * r
    double circumference = 2 * pi * r;  // Utiliser directement π en double précision
    cout << "Le rayon est " << r << ", circonférence : " << circumference << endl;  // Sortie : 31.4159

    // 2. Calculer l'aire du cercle : π * r²
    double area = pi * pow(r, 2);
    cout << "Le rayon est " << r << ", aire : " << area << endl;  // Sortie : 78.5398

    // 3. Version à haute précision (long double)
    long double r_ld = 5.0L;
    long double area_ld = pi_v<long double> * powl(r_ld, 2);  // powl est la version long double de pow
    cout << "Aire du cercle à haute précision : " << area_ld << endl;  // Affiche une valeur plus précise : 78.53981633974483...

    return 0;
}

Exemple 2 : constante e

Constante naturelle e et calculs exponentiels :

Exemple

#include <iostream>
#include <numbers>
#include <cmath>

using namespace std;
using namespace std::numbers;

int main() {
    // Calcul de l'exponentielle naturelle : e^x (la fonction exp est la fonction exponentielle dans cmath)
    double x = 2.0;
    double exp_result = exp(x);          // Calculer manuellement e^2
    double exp_result_direct = pow(e, x); // Calculer e^2 en utilisant numbers::e
    cout << "e^2 = " << exp_result << endl;          // Sortie : 7.38906
    cout << "e^2 (calcul direct) = " << exp_result_direct << endl;  // Les résultats sont cohérents

    return 0;
}

Exemple 3 : nombre d'or

Application du nombre d'or φ :

Exemple

#include <iostream>
#include <numbers>

using namespace std;
using namespace std::numbers;

int main() {
    // Nombre d'or : lorsque longueur/largeur = φ, c'est un rectangle d'or
    double width = 10.0;
    double golden_height = width * phi;  // Hauteur du rectangle d'or
    cout << "La largeur est " << width << ", la hauteur du rectangle d'or : " << golden_height << endl;  // Sortie : 16.1803

    // Vérifier la définition mathématique de φ : φ = (1 + √5)/2
    double phi_manual = (1 + sqrt(5.0)) / 2;
    cout << "Nombre d'or calculé manuellement : " << phi_manual << endl;  // Cohérent avec numbers::phi

    return 0;
}

Exemple 4 : types à virgule flottante

Adaptation des constantes pour différents types à virgule flottante :

Exemple

#include <iostream>
#include <numbers>
#include <iomanip> // utilisé pour définir la précision de sortie

using namespace std;

int main() {
    // Définir une sortie de haute précision (afficher 15 décimales)
    cout << fixed << setprecision(15);

    // version float de π (simple précision)
    float pi_float = std::numbers::pi_v<float>;
    cout << "float π : " << pi_float << endl;  // Sortie : 3.141592741012573

    // version double de π (double précision, par défaut)
    double pi_double = std::numbers::pi;
    cout << "double π: " << pi_double << endl;  // Sortie : 3.141592653589793

    // version long double de π (haute précision)
    long double pi_long_double = std::numbers::pi_v<long double>;
    cout << "long double π: " << pi_long_double << endl;  // Affiche la valeur plus précise 3.1415926535897932385...

    return 0;
}
autres extensions