namespace std {
float
hypot(float x,
float y); // (1) C++11からC++20まで
double
hypot(double x,
double y); // (2) C++11からC++20まで
long double
hypot(long double x,
long double y); // (3) C++11からC++20まで
floating-point-type
hypot(floating-point-type x,
floating-point-type y); // (4) C++23
constexpr floating-point-type
hypot(floating-point-type x,
floating-point-type y); // (4) C++26
Promoted
hypot(Arithmetic1 x,
Arithmetic2 y); // (5) C++11
constexpr Promoted
hypot(Arithmetic1 x,
Arithmetic2 y); // (5) C++26
float
hypotf(float x,
float y); // (6) C++17
constexpr float
hypotf(float x,
float y); // (6) C++26
long double
hypotl(long double x,
long double y); // (7) C++17
constexpr long double
hypotl(long double x,
long double y); // (7) C++26
float
hypot(float x,
float y,
float z); // (8) C++17からC++20まで
double
hypot(double x,
double y,
double z); // (9) C++17からC++20まで
long double
hypot(long double x,
long double y,
long double z); // (10) C++17からC++20まで
floating-point-type
hypot(floating-point-type x,
floating-point-type y,
floating-point-type z); // (11) C++23
constexpr floating-point-type
hypot(floating-point-type x,
floating-point-type y,
floating-point-type z); // (11) C++26
Promoted
hypot(Arithmetic1 x,
Arithmetic2 y,
Arithmetic3 z); // (12) C++17
constexpr Promoted
hypot(Arithmetic1 x,
Arithmetic2 y,
Arithmetic3 z); // (12) C++26
}
概要
算術型の平方和の平方根を求める。この際、余計なオーバーフロー、アンダーフローを起こさない。hypot は hypotenuse((直角三角形の)斜辺)の略。
この関数は、「三平方の定理」によって、直角三角形の斜辺の長さを求めるために使用できる。直角三角形において、直角に隣接する辺aとb、および斜辺cがあったとき、辺の長さは、三平方の定理によって以下の関係が成り立つ:
a2 + b2 = c2
この関数の効果である以下の式は、三平方の定理の式変形である:
a2 + b2
はc2
と等しくなるため、2乗の和に対する平方根を求めることで、斜辺cの長さが求まる。つまり、この関数に引数として、直角に隣接する辺aとbの長さを与えることで、戻り値として斜辺cの長さが返される。
各オーバーロードの概要は、以下の通りである:
- (1) : 2引数版の
float
に対するオーバーロード - (2) : 2引数版の
double
に対するオーバーロード - (3) : 2引数版の
long double
に対するオーバーロード - (4) : 2引数版の浮動小数点数型に対するオーバーロード
- (5) : 2引数版の算術型に対するオーバーロード (大きい精度にキャストして計算される。整数は
double
で計算される) - (6) : 2引数版の
float
型規定 - (7) : 2引数版の
long double
型規定 - (8) : 3引数版の
float
に対するオーバーロード - (9) : 3引数版の
double
に対するオーバーロード - (10) : 3引数版の
long double
に対するオーバーロード - (11) : 3引数版の浮動小数点数型に対するオーバーロード
- (12) : 3引数版の算術型に対するオーバーロード (大きい精度にキャストして計算される。整数は
double
で計算される)
戻り値
- (1)-(7) : 引数
x
と引数y
の平方和の平方根を返す。 - (8)-(12) : 引数
x
、引数y
、引数z
の平方和の平方根を返す。
オーバーフローエラー、アンダーフローエラーが発生する可能性がある。
備考
- (1)-(7) :
- (8)-(12) :
- 概要の「余計なオーバーフロー、アンダーフローを起こさない」とは、たとえ
x2
が戻り値型の範囲を超えていても、結果が戻り値型の範囲に収まるのであればオーバーフローしないで正しい結果を返す、と言う事である。 - オーバーフローエラー、アンダーフローエラーが発生した場合の挙動については、
<cmath>
を参照。 - 処理系が IEC 60559 に準拠している場合(
std::numeric_limits<T>::is_iec559() != false
)、以下の規定が追加される。hypot(x, y)
とhypot(y, x)
とhypot(x, -y)
は等価である。hypot(x, ±0)
は、fabs(x)
と等価である。hypot(±∞, y)
の戻り値は、たとえy
が NaN の場合でも+∞
となる。
- C++23では、(1)、(2)、(3)が(4)に統合、(8)、(9)、(10)が(11)に統合され、拡張浮動小数点数型を含む浮動小数点数型へのオーバーロードとして定義された
例
基本的な使い方
#include <cmath>
#include <limits>
#include <iostream>
int main() {
// 2引数版
std::cout << std::fixed;
std::cout << "hypot(0.0, 0.0) = " << std::hypot(0.0, 0.0) << std::endl;
std::cout << "hypot(1.0, 1.0) = " << std::hypot(1.0, 1.0) << std::endl;
std::cout << "hypot(3.0, 4.0) = " << std::hypot(3.0, 4.0) << std::endl;
std::cout << "hypot(+∞, NaN) = " << std::hypot(std::numeric_limits<double>::infinity(),
std::numeric_limits<double>::quiet_NaN())
<< std::endl;
// 3引数版
std::cout << "hypot(3.0, 4.0, 2.0) = " << std::hypot(3.0, 4.0, 2.0) << std::endl;
}
xxxxxxxxxx
#include <cmath>
#include <limits>
#include <iostream>
int main() {
// 2引数版
std::cout << std::fixed;
std::cout << "hypot(0.0, 0.0) = " << std::hypot(0.0, 0.0) << std::endl;
std::cout << "hypot(1.0, 1.0) = " << std::hypot(1.0, 1.0) << std::endl;
std::cout << "hypot(3.0, 4.0) = " << std::hypot(3.0, 4.0) << std::endl;
std::cout << "hypot(+∞, NaN) = " << std::hypot(std::numeric_limits<double>::infinity(),
std::numeric_limits<double>::quiet_NaN())
<< std::endl;
// 3引数版
std::cout << "hypot(3.0, 4.0, 2.0) = " << std::hypot(3.0, 4.0, 2.0) << std::endl;
}
出力
hypot(0.0, 0.0) = 0.000000
hypot(1.0, 1.0) = 1.414214
hypot(3.0, 4.0) = 5.000000
hypot(+∞, NaN) = inf
hypot(3.0, 4.0, 2.0) = 5.385165
ベクトルの長さを求める
#include <iostream>
#include <cmath>
// 2次元ベクトル
struct Vector2 {
double x = 0;
double y = 0;
// ベクトルの長さ。
// ノルム (norm) とも呼ばれる
double length() const
{
return std::hypot(x, y);
}
};
// 3次元ベクトル
struct Vector3 {
double x = 0;
double y = 0;
double z = 0;
double length() const
{
return std::hypot(x, y, z);
}
};
int main()
{
std::cout << Vector2{3.0, 3.0}.length() << std::endl;
std::cout << Vector3{3.0, 2.0, 4.0}.length() << std::endl;
}
34
std::cout << Vector3{3.0, 2.0, 4.0}.length() << std::endl;
#include <iostream>
#include <cmath>
// 2次元ベクトル
struct Vector2 {
double x = 0;
double y = 0;
// ベクトルの長さ。
// ノルム (norm) とも呼ばれる
double length() const
{
return std::hypot(x, y);
}
};
// 3次元ベクトル
struct Vector3 {
出力
4.24264
5.38516
バージョン
言語
- C++11
処理系
- Clang: 2.9 ✅, 3.1 ✅
- GCC: 4.3.4 ✅, 4.4.5 ✅, 4.5.2 ✅, 4.6.1 ✅, 4.7.0 ✅
- Visual C++: 2012 ✅, 2013 ✅, 2015 ✅, 2017 ✅
- 2002, 2003, 2005, 2008, 2010およびそれ以降では、
<math.h>
でグローバル名前空間に以下が定義されている。- 仮引数・戻り値が
float
型の_hypotf
関数が定義されている。 - 仮引数・戻り値が
double
型のhypot
関数と_hypot
関数が定義されている。 - 仮引数・戻り値が
long double
型の_hypotl
マクロが定義されている。
- 仮引数・戻り値が
- 2010, 2012およびそれ以降では、上記に加え
<math.h>
でグローバル名前空間に以下が定義されている。- 仮引数・戻り値が
float
型のhypotf
関数が定義されている。 - 仮引数・戻り値が
long double
型のhypotl
マクロが定義されている。
- 仮引数・戻り値が
- 2013以降、
_hypotl
とhypotl
は関数として定義されている。
- 2002, 2003, 2005, 2008, 2010およびそれ以降では、
備考
特定の環境では、早期に constexpr
対応されている場合がある:
- GCC 4.6.1 以上
実装例
fabs
と sqrt
があれば、以下のように変換しても求められる。