Question

How to Use Pi and Trigonometric Functions in C++

cpptrigonometry

Question

I want to use the value of pi together with trigonometric functions in a C++ program. I can access trigonometric functions by including math.h, but I cannot find a built-in definition for pi in that header.

How can I use pi in C++ without manually defining it myself?

Short Answer

By the end of this page, you will understand how C++ provides trigonometric functions, why pi is not always available as a simple global constant, and the recommended ways to access it in modern C++. You will also see practical examples using std::sin, std::cos, and std::numbers::pi.

Concept

C++ provides many mathematical functions such as sin, cos, tan, and sqrt, but mathematical constants like pi have historically been handled differently.

The important idea is this:

  • cmath gives you math functions
  • Pi is a constant, not a function
  • Older C++ code often used non-standard macros like M_PI
  • Modern C++ provides a standard way: std::numbers::pi

Why this matters

If you are writing code that uses angles, circles, graphics, simulations, or physics, you will need pi frequently. Using a reliable source for pi helps make your code:

  • more readable
  • more portable
  • more precise
  • more standard-compliant

The old situation

In C and older C++ code, developers often included:

#include <math.h>

and hoped to get M_PI. The problem is that M_PI is not part of the C++ standard. Some compilers provide it, some do not, and some require extra settings.

The modern C++ solution

Since C++20, the standard library includes mathematical constants in the <numbers> header:

#include <numbers>

You can then use:

std::numbers::pi

There are also typed versions such as:

std::numbers::pi_v<double>
std::numbers::pi_v<float>
std::numbers::pi_v<long double>

This is the best standard solution in modern C++.

Use cmath instead of math.h

In C++, prefer:

#include <cmath>

instead of:

#include <math.h>

<cmath> places functions in the std namespace, so you typically write:

std::sin(...)
std::cos(...)

Mental Model

Think of <cmath> as a toolbox of math operations and <numbers> as a reference sheet of math constants.

  • Need to calculate something? Use the toolbox: std::sin, std::cos, std::sqrt
  • Need a known fixed value? Use the reference sheet: std::numbers::pi

Pi is like a universal measuring reference. You do not "compute" it each time you need it. You simply look it up from a trusted source.

Take Quiz

Syntax and Examples

In modern C++, the recommended approach is:

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

int main() {
    double radius = 5.0;
    double area = std::numbers::pi * radius * radius;

    std::cout << "Area: " << area << '\n';
    std::cout << "sin(pi / 2): " << std::sin(std::numbers::pi / 2) << '\n';
}

What this does

  • <cmath> provides std::sin
  • <numbers> provides std::numbers::pi
  • std::numbers::pi / 2 represents 90 degrees in radians

Typed pi constants

If you want a specific type, use pi_v<T>:

#include <iostream>
#include <numbers>

int main() {
    float pi_f = std::numbers::pi_v<float>;
    double pi_d = std::numbers::pi_v<double>;
    long double pi_ld = std::numbers::pi_v<long double>;

    std::cout << pi_f << '\n';
    std::cout << pi_d << '\n';
    std::cout << pi_ld << '\n';
}

If you are using pre-C++20

If your compiler does not support <numbers>, you may need to define your own constant:

#include <iostream>
#include <cmath>

int main() {
    constexpr double pi = 3.14159265358979323846;
    std::cout << std::sin(pi / 2) << '\n';
}

This is often better than relying on M_PI, because it is explicit and portable.

Non-standard M_PI

Some systems support:

#include <cmath>
#include <iostream>

int main() {
    std::cout << M_PI << '\n';
}

But this is not guaranteed to work everywhere, so avoid depending on it in portable C++ code.

Step by Step Execution

Consider this example:

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

int main() {
    double angle = std::numbers::pi / 2;
    double result = std::sin(angle);

    std::cout << result << '\n';
}

Step by step

  1. #include <iostream> lets the program print output.
  2. #include <cmath> gives access to math functions like std::sin.
  3. #include <numbers> gives access to std::numbers::pi.
  4. double angle = std::numbers::pi / 2;
    • This stores half of pi.
    • Half of pi radians is 90 degrees.
  5. double result = std::sin(angle);
    • std::sin expects the angle in radians, not degrees.
    • sin(pi / 2) is mathematically 1.
  6. std::cout << result << '\n';
    • Prints the result.

Expected output

1

In practice, floating-point output may sometimes look like this:

0.999999

That is normal due to floating-point precision.

Real World Use Cases

Pi appears in many kinds of software:

Graphics and game development

  • rotating objects using radians
  • drawing circles and arcs
  • computing wave motion
double angle = std::numbers::pi / 4;
double x = std::cos(angle);
double y = std::sin(angle);

Scientific and engineering software

  • orbital calculations
  • signal processing
  • geometry formulas
  • simulations

Data visualization

  • polar charts
  • circular gauges
  • radar plots

Robotics and embedded systems

  • wheel rotation calculations
  • motor angle conversion
  • sensor orientation math

Education and scripting tools

  • math utilities
  • unit converters
  • trigonometry demos
Take Quiz

Real Codebase Usage

In real projects, developers usually combine mathematical constants with a few common patterns.

1. Prefer standard headers and namespaces

Use:

#include <cmath>
#include <numbers>

and call functions explicitly:

std::sin(value)
std::cos(value)
std::numbers::pi

This avoids ambiguity and makes code easier to read.

2. Convert degrees to radians

Many real applications receive degrees from users, files, or APIs, but C++ trig functions use radians.

#include <numbers>

double degrees_to_radians(double degrees) {
    return degrees * std::numbers::pi / 180.0;
}

This helper function is common in codebases.

3. Use constexpr for reusable constants

If you are not on C++20, teams often define a local constant:

constexpr double pi = 3.14159265358979323846;

constexpr allows compile-time evaluation and makes the value clearly intentional.

4. Guard against wrong units

A very common source of bugs is mixing degrees and radians. Developers often name variables clearly:

double angle_radians = std::numbers::pi / 3;
double angle_degrees = 60.0;

5. Wrap formulas in small functions

Instead of repeating formulas everywhere:

double circle_area(double radius) {
    return std::numbers::pi * radius * radius;
}

This improves reuse and reduces mistakes.

Common Mistakes

1. Using math.h instead of cmath

Less idiomatic C++

#include <math.h>

Better C++

#include <cmath>

In C++, prefer the standard C++ header.

2. Expecting M_PI to always exist

Broken assumption:

#include <cmath>
#include <iostream>

int main() {
    std::cout << M_PI << '\n';
}

This may fail on some compilers because M_PI is non-standard.

Use:

std::numbers::pi

or define your own constexpr constant if needed.

3. Forgetting the std:: namespace

Broken code:

double x = sin(3.14 / 2);

Preferred:

double x = std::sin(std::numbers::pi / 2);

4. Passing degrees directly to trig functions

Broken logic:

std::cout << std::sin(90) << '\n';

This treats 90 as 90 radians, not 90 degrees.

Correct approach:

double radians = 90.0 * std::numbers::pi / 180.0;
std::cout << std::sin(radians) << '\n';

5. Using low-precision values of pi

Less accurate:

constexpr double pi = 3.14;

Better:

constexpr double pi = 3.14159265358979323846;

6. Comparing floating-point results for exact equality

Risky:

if (std::sin(std::numbers::pi / 2) == 1.0) {
    // may not always behave as expected
}

Better:

#include <cmath>

if (std::abs(std::sin(std::numbers::pi / 2) - 1.0) < 1e-9) {
    // close enough
}

Comparisons

OptionStandard?Recommended?Notes
std::numbers::piYes, C++20+YesBest modern standard solution
std::numbers::pi_v<double>Yes, C++20+YesUseful when you want a specific type
M_PINoNoCommon on some platforms, but non-standard
constexpr double pi = ...YesYes for pre-C++20Portable fallback

<cmath> vs <math.h>

HeaderLanguage styleNamespace behaviorRecommended in C++?
<cmath>C++Usually in stdYes
<math.h>C styleOlder style/global compatibilityNo

Pi constant vs calculating with literals

ApproachExampleGood choice?
Named constantstd::numbers::piYes
Manual literal in many places3.14159265358979323846 repeated everywhereNo
Short approximation3.14Usually no
Take Quiz

Cheat Sheet

// Modern C++
#include <cmath>
#include <numbers>

double x = std::numbers::pi;
double y = std::sin(std::numbers::pi / 2);
// Typed versions
float pf = std::numbers::pi_v<float>;
double pd = std::numbers::pi_v<double>;
long double pld = std::numbers::pi_v<long double>;
// Pre-C++20 fallback
constexpr double pi = 3.14159265358979323846;

Quick rules

  • Prefer <cmath> over <math.h>
  • Prefer std::numbers::pi in C++20+
  • Do not rely on M_PI for portable code
  • std::sin, std::cos, and std::tan use radians
  • Convert degrees to radians with:
degrees * pi / 180.0

Common formulas

// Circle area
area = pi * r * r;

// Circle circumference
circumference = 2 * pi * r;

// Degrees to radians
radians = degrees * pi / 180.0;

// Radians to degrees
degrees = radians * 180.0 / pi;

FAQ

Why does C++ not always provide M_PI?

M_PI is not part of the C++ standard. Some compilers or libraries provide it as an extension, but portable C++ code should not depend on it.

What is the standard way to get pi in modern C++?

Use std::numbers::pi from the <numbers> header in C++20 and later.

Should I use <math.h> or <cmath> in C++?

Use <cmath>. It is the C++ version of the math header and works better with the std namespace.

Do C++ trigonometric functions use degrees or radians?

They use radians. If you have degrees, convert them first.

What if my compiler does not support <numbers>?

Use a local constexpr constant such as:

constexpr double pi = 3.14159265358979323846;

Is std::numbers::pi better than writing 3.14159265358979323846 directly?

Yes. It is clearer, standard, and avoids repeating the literal throughout your code.

Can I use float or long double versions of pi?

Yes. Use std::numbers::pi_v<float> or std::numbers::pi_v<long double> when you want a specific type.

Take Quiz

Mini Project

Description

Build a small C++ program that calculates circle properties and evaluates a trigonometric value from a degree input. This project demonstrates how to use pi correctly, how to convert degrees to radians, and how to call standard math functions in practical code.

Goal

Create a program that reads a radius and an angle in degrees, then prints the circle area, circumference, and the sine of the angle.

Requirements

  1. Read a circle radius from the user.
  2. Read an angle in degrees from the user.
  3. Use a standard pi source where available.
  4. Convert the degree input to radians before calling std::sin.
  5. Print the area, circumference, and sine result clearly.
Take Quiz

Keep learning

Related questions

View more