Standard Library[lib]
C++ sqrt: square root with std::sqrt and cmath
- Section
- Standard Library [lib]
- Standard
- C++17
- Compilers
- MSVC 19.44, Clang 19.1 (MSVC STL), GCC 16.2, Clang 23.1 (libc++)
- Published
- Length
- 6 min read
In this answer7 clauses
- 1What does sqrt return for an int, a float or a double?
- 2What does sqrt of a negative number return?
- 3How do you check for a perfect square in C++?
- 4Should you use sqrt or pow(x, 0.5)?
- 5How do you take a cube root or another root?
- 6How do you find a square root without sqrt?
- 7Which function for which root?
Abstract
std::sqrt from <cmath> returns the square root of a number: std::sqrt(25.0) is 5. A float gives a float and a double a double; an int is treated as a double, so the result is a double, and storing it in an int cuts the decimals off. A negative argument returns NaN, which std::isnan detects. std::cbrt takes cube roots, std::pow(x, 1.0 / n) other roots, and std::hypot the long side of a right triangle.

std::sqrt in C++ returns the square root of a number: std::sqrt(25.0) is 5. Include <cmath> to use it. Given an int, it returns a double, and given a negative number it returns NaN, “not a number”, which you test for with std::isnan. For a cube root, call std::cbrt.
A whole program that prints two square roots:
#include <cmath>
#include <iostream>
int main() {
std::cout << std::sqrt(25.0) << '\n'; // 5
std::cout << std::sqrt(2.0) << '\n'; // 1.41421
}— end example]
It printed:
5
1.41421— end example]
The first result is the double 5.0, which std::cout printed as 5, and it printed six digits of the second. The samples are C++17, built with MSVC 19.44, Clang 19.1 (MSVC STL), GCC 16.2 and Clang 23.1 (libc++). All four printed the same numbers; only the spelling of NaN differed. Since When lists, for each standard, the first compiler releases that support it.

What does sqrt return for an int, a float or a double?
For a float the sqrt function returns a float, and for a double a double. A whole number such as an int is treated as a double first (the standard’s <cmath> synopsis), so std::sqrt(10) returns a double as well. The samples checked each type with std::is_same_v, which is true when two types are the same:
auto from_float = std::sqrt(2.0f);
auto from_double = std::sqrt(2.0);
auto from_int = std::sqrt(10); // 10 becomes 10.0 first
std::cout << std::boolalpha;
std::cout << std::is_same_v<decltype(from_float), float> << '\n';
std::cout << std::is_same_v<decltype(from_double), double> << '\n';
std::cout << std::is_same_v<decltype(from_int), double> << '\n';
std::cout << from_int << '\n'; // 3.16228
int root = std::sqrt(10); // the decimals are cut off
std::cout << root << '\n'; // 3— end example]
All four printed true three times, then 3.16228 and 3. Storing the result in an int cuts the decimals off: 3.16228 became 3. Only MSVC warned (C4244 at /W4); GCC and both Clangs were silent at -Wall -Wextra. What an int and a double can each hold is in C++ data types.
What does sqrt of a negative number return?
NaN, a special value a double or a float can hold, meaning “not a number”. The program does not stop and no exception is thrown, so test the result with std::isnan, which returns true for a NaN. Better still, check the number before the call, so a negative one never reaches std::sqrt:
double root = std::sqrt(-4.0);
std::cout << root << '\n'; // NaN, spelled by the library
std::cout << std::boolalpha;
std::cout << std::isnan(root) << '\n'; // true
double x = -4.0;
if (x < 0) {
std::cout << "no real square root\n";
} else {
std::cout << std::sqrt(x) << '\n';
}— end example]
On Windows, MSVC and Clang 19.1 (both on Microsoft’s library) printed:
-nan(ind)
true
no real square root— end example]
GCC 16.2 and Clang 23.1 with libc++, both on Linux, printed -nan on the first line. The spelling belongs to the standard library, so never compare the printed text: call std::isnan.
How do you check for a perfect square in C++?
Take the square root, round it to the nearest whole number with std::lround, square that, and compare it with the number:
bool is_perfect_square(int n) {
if (n < 0) {
return false; // no negative number is a square
}
long long root = std::lround(std::sqrt(n)); // nearest whole
return root * root == n;
}
int main() {
std::cout << std::boolalpha;
std::cout << is_perfect_square(49) << '\n'; // true
std::cout << is_perfect_square(50) << '\n'; // false
std::cout << is_perfect_square(2147395600) << '\n'; // true
}— end example]
All four printed true, false and true. The rounded root goes in a long long because from 2,147,441,941 up it rounds to 46,341, whose square is too big for a 4-byte long, the type std::lround returns on Windows.
2,147,395,600 is 46,340 squared, the largest square a 4-byte int holds. The samples also ran the function over every square from 1 up to that one, 46,340 of them, and over each of them plus one: it answered correctly every time, on all four.
Should you use sqrt or pow(x, 0.5)?
Use std::sqrt: it says what it does. std::pow with an exponent of 0.5 is also a square root, and in the samples it gave exactly the same double:
double by_sqrt = std::sqrt(x);
double by_pow = std::pow(x, 0.5);
// ...
std::cout << (by_sqrt == by_pow) << '\n';— end example]
Printed with 17 significant digits, set with std:: as in formatting numbers with cout, and with std::boolalpha, all four gave for 2.0:
1.4142135623730951
1.4142135623730951
true— end example]
For 10.0 and 1e300 the two were equal too. That is what these builds did, not a promise: the IEEE floating-point standard requires std::sqrt to be correctly rounded, exact whenever the root can be held exactly in a double, and std::pow is “not so constrained” (cppreference on std::sqrt).
How do you take a cube root or another root?
Call std::cbrt for a cube root and std::pow(x, 1.0 / n) for the n-th root. Write 1.0, not 1: with an int n, 1 / n divides two whole numbers and gives 0, so std:: printed 1 on all four. For the long side of a right triangle, such as the diagonal of a 3 by 4 rectangle, std::hypot takes the two sides:
std::cout << std::cbrt(27.0) << '\n'; // 3
std::cout << std::cbrt(-8.0) << '\n'; // -2
std::cout << std::pow(81.0, 1.0 / 4) << '\n'; // 3
std::cout << std::hypot(3.0, 4.0) << '\n'; // 5— end example]
All four printed 3, -2, 3 and 5. std::cbrt accepts a negative number. std::pow with a negative base and a fractional exponent, such as 1.0 / 3, returns NaN instead, so take the cube root of a negative number with std::cbrt. std::hypot squares the sides for you, without undue overflow along the way, and since C++17 it takes a third argument, for a distance in three dimensions.
How do you find a square root without sqrt?
With Newton’s method: start from a guess, then replace it, round after round, with the average of the guess and the number divided by the guess:
double x = 2.0;
double guess = 1.0; // any positive start works
std::cout << std::setprecision(10);
for (int round = 1; round <= 6; ++round) {
guess = (guess + x / guess) / 2; // average of guess and x/guess
std::cout << guess << '\n';
}
std::cout << std::sqrt(x) << '\n';— end example]
It printed:
1.5
1.416666667
1.414215686
1.414213562
1.414213562
1.414213562
1.414213562— end example]
The fourth round already printed 1.414213562, the same ten digits as std::sqrt(2.0) on the last line, and rounds five and six changed nothing at that precision. It makes a good exercise; in code you ship, call std::sqrt.
Which function for which root?
| You need | Call |
|---|---|
| The square root | std::sqrt(x) |
| The square root as a whole number | std:: |
| The cube root, negatives included | std::cbrt(x) |
| The n-th root of a positive number | std::pow(x, 1.0 / n) |
| The long side of a right triangle | std::hypot(a, b) |
| To know whether a result is NaN | std::isnan(result) |
Standard library has the rest of the library’s answers.
Questions
How do you find the square root of a number in C++?
std::sqrt is declared in <cmath>: write #include <cmath> and call std::sqrt(x). The same header has std::isnan, which tests a result for NaN, and std::cbrt, the cube root.
What does sqrt return in C++?
A double for a double or a whole-number argument, a float for a float, and a long double for a long double. std::sqrt(10) returns the double 3.16228..., not an int. For a negative argument the value it returns is NaN, not a number.
What is the square root of a negative number in C++?
std::sqrt returns NaN, not a number, for an argument below zero, and the program keeps running. Test the result with std::isnan from <cmath>, or check that the number is not negative before the call. Do not compare the printed text: Microsoft's library prints -nan(ind), and GCC's library and libc++ on Linux print -nan.
How do you get a square root as an int in C++?
Round it with std::lround(std::sqrt(x)), which returns the nearest whole number as a long: 4 for 15. Assigning the result to an int, as in int root = std::sqrt(15);, cuts the decimals off instead and stores 3, the whole part.
What is the difference between sqrt, sqrtf and sqrtl?
sqrtf and sqrtl are the names C uses for the float and long double versions of sqrt, and C++ has them too, as std::sqrtf and std::sqrtl since C++11. In C++ you rarely need them: std::sqrt picks the float, double or long double version from the type of its argument.
Is std::sqrt constexpr?
From C++26 it is, so it can be evaluated at compile time. In C++17, C++20 and C++23 the standard does not declare it constexpr, so portable code cannot use it in a constant expression, such as the initializer of a constexpr variable.
Sources
- std::sqrt, std::sqrtf, std::sqrtlcppreference.com
- [cmath.syn] Header cmath synopsisC++ standard working draft
- std::isnancppreference.com
- std::round, std::lround, std::llroundcppreference.com
- std::powcppreference.com
- std::cbrtcppreference.com
- std::hypotcppreference.com