0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

20年ぶりくらいに abs(浮動小数点数) でバグる

0
Last updated at Posted at 2026-02-06

馬鹿な話

Visual Studio でコード書いたよ! 元気に動くよ! やったね!

g++ でビルドすると挙動が変になるよ! イミワカンネー.

探っていくと,以下のような if に全くヒットしないという状況になっていた.

要素がfloat3次元ベクトル型 V = 結果が単位ベクトルになる演算();
if( abs(V.y) >= sin(適当な角度値) )  //ベクトルの向きで分岐
{
  /* g++ だとここに来なくなるよ! */
}

float に対しての abs() とか……なんとも懐かしい感じのミスだな.

つまり「挙動が変になる」んじゃなくて,書いたとおりにバグっているというだけのことだ.OK.
std::abs() に直せば終了だ.よかった.

え? そしたら「元気に動く」方がおかしくね? 何なの?

どうやら Visual Studio だと, abs() と書いたところが勝手に std::abs() に(?)なってるように見える.

sin() とかも同様.
なので, 適当な角度値 のところが float だったりすると, double と float との間での型変換という話になるか否かが VS と g++ とで異なってくるハズ.

どういうからくりなのか?

どこぞのヘッダに using std::abs; みたいなのが書かれているんだろうか…?
とか思い abs() の定義を調べてみたら,そうではなくて,単にグローバルな名前空間に abs(float); とかが用意されてるのね.

//こんな感じのオーバーロードがあって…
float abs( float );
double abs( double );

//std::abs の側をこうしてある
namespace std{
  using ::abs;
}

そんなわけで

std:: を書き忘れないようにすべし,ってことか.

「ここには abs を山ほどたくさん書くので…」みたいな場合には using std::abs; を書くとかで.

0
0
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?