シューティングにおける数学的計算について

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
DD SS

シューティングにおける数学的計算について

#1

投稿記事 by DD SS » 17年前

いつもHPの方を参考にさせていただいてます^^
特に今STGの制作をしているので龍神録のほうを見ながら勉強をしているところです。

今回はその龍神録の 第12章、たくさんの敵の行動パターンを作ってみよう のsin,cos関数について質問を
しようと思います。

msdnの方や他の方々のHPを参考に
sin関数やcos関数の働きを見てるんですがどうして 
■ラジアンを出すときにcosを使うのか
■Enemy_act関数の xには cos を yには sinを使うのか
というのがよくわかりません。
また
if (t % 60 == 0) {
    int r = cos(enemy.ang) < 0 ? 0 : 1;
    enemy.sp = 6 + rang(2);
    enemy.ang = rang(PI / 4) + PI + r;
    enemy.muki = 2 - 2 * r;
}

この一連の動作も良く分からないままです;

sinやcosに引数を0~360まで渡してその戻り値を調べるっていう方法もやってみたのですが・・・
自分が思ってる値と異なる値が返ってきて余計に混乱してしまいます。↓がそのコードです。
#include <stdio.h>
#include <math.h>

int main(void) {
    double s, c, t;
    double i;
    int w, k;
    s = c = t = 0.0;
    w = 1;
    while (w) {
        for (i = 0.0; i < 361; i++) {
            s = sin(i);
            c = cos(i);
            t = tan(i);
            printf("i = %lf sin = %lf cos = %lf tan = %lf \n",i , s, c, t);
        }
        w -= 1;
    }
    scanf("%d", &k);
    return 0;
}

もしかしたら自分の数学に対しての努力と知識が足りないだけかもしれませんが、
何か助言をいただけると幸いです。

お忙しいとは思いますが、ご返答のほどよろしくお願いします。
龍神録の更新楽しみにしてます^^。 がんばってください!

管理人

Re:シューティングにおける数学的計算について

#2

投稿記事 by 管理人 » 17年前

こんにちは。
館の方参考にしてくださってありがとうございます。

>■ラジアンを出すときにcosを使うのか
>■Enemy_act関数の xには cos を yには sinを使うのか

ということですが、「ラジアンを出す時cosを使う」のではなく、
「sin,cosを使うとき、ラジアンを使う」ということでいいですか?
角度の用いた計算方法は弧度法と度数法がありますよね。
円一周を360°とする度数法に対し、弧度法は円一周を2πとします。
πは円周率ですね。
sin,cosなどの関数は弧度法の引数が要求されますから、
ラジアンで渡す必要があります。
どうしてもラジアンによる計算に抵抗があるようなら、自前でsin,cos関数を実装してはどうでしょうか。
0°は弧度法でも0です。360°が2*3.1415926535ですから、対応を考えれば実装出来ますよね。
for (i = 0.0; i < 361; i++) {
            s = sin(i);
なので、弧度法、度数法の仕様にあっていないために、これが計算出来ないわけですが、
自前で度数法による引数が渡せる関数を作ればこれが渡せるようになりますね。

もしこの辺の話がよくわからなければ、
http://www.google.co.jp/search?hl=ja&q= ... =&aq=f&oq=
この辺で復習してみてはいかがでしょうか。

DDSS

Re:シューティングにおける数学的計算について

#3

投稿記事 by DDSS » 17年前

返信ありがとうございます。

自分で作った方のプログラムについては
戻り値が期待通り戻ってこなかったかわかりました^^

>■ラジアンを出すときにcosを使うのか
なんですが ラジアンじゃなく半径かもしれません;
>int r = cos(enemy.ang) < 0 ? 0 : 1;
この部分のrなんですがラジアンと勘違いしてしまいました。

これで質問しようと思ったんですが勘違いで自分が持ってる質問とは違った質問をしてしまいました。

ここでまた質問なんですが
■rを出すときにcosを使うのか
ということです。
また
>■Enemy_act関数の xには cos を yには sinを使うのか
ということもまだちょっとわからないです。

何度もすみませんが、よろしくお願いします。

管理人

Re:シューティングにおける数学的計算について

#4

投稿記事 by 管理人 » 17年前

あぁ、これは確かにわかりにくいかき方ですね。
まず、条件演算子というものはご存知でしょうか。

(1)
int a=0;
int b;
b = a==0 ? 1 : 0;

(2)
int a=0;
int b;
if(a==0)
    b=1;
else
    b=0;

(1)と(2)は同じ意味です。よくわからなければ、「条件演算子」でググってみてください。

また、第一象限~第四象限についてはご存知でしょうか?
原点を基準にangleの方向が第一象限、第四象限はcosがプラスになり、
第二象限、第三象限はマイナスになりますよね。
それを利用して、現在向いてる方向が第一象限か第四象限ならrを1にし、
違うなら0を代入しています。
なぜそんな事をしたいかというと、向いている向きを交互にさせたいからです。
 →
←
 →
←
 →
と向かせたいのです。
単純にrang(PI/4)の計算結果は-PI/4~PI/4ですから右側です。
もし現在向いている向きが右側なら左側に向かせ、左側なら右側にむかせたいのです。
ということは、右側なら、計算結果+PIすればよく、左側なら計算結果+0にすればよいです。
ということは

      int r=cos(enemy.ang)< 0 ? 0 : 1;
      //「左向き」の条件が正しければrに0をいれ、偽なら1を入れる
      enemy.ang=rang(PI/4)+PI*r;
      //左向きなら計算結果+0、右向きなら計算結果+PI

という計算式の意味がわかってきませんか?

      enemy.muki=2-2*r;

これは単に敵の向きをセットしているだけですね。

管理人

Re:シューティングにおける数学的計算について

#5

投稿記事 by 管理人 » 17年前

何故x成分の計算にはcosを使うか、y成分の計算にはsinを使うかという事に関しては
三角関数の知識が必要です。
上記紹介したリンク先はご覧になりましたでしょうか?

lbfuvab

Re:シューティングにおける数学的計算について

#6

投稿記事 by lbfuvab » 17年前

sin,cos等の関数で度数で扱いたい場合

#define RAD(ang) ((ang)*3.14159/180.0)

とかを定義するのもありですね。

DDSS

Re:シューティングにおける数学的計算について

#7

投稿記事 by DDSS » 17年前

管理人さん lbfuvabさん 返信ありがとうございます。

rの方ですがわかりやすい説明でとてもよくわかりました^^
x成分,y成分のほうは
まだちょっとわからない部分があるんですが、
↑のURLを参考に頭を整理してがんばって解いていきたいと思います。

ありがとうございました^^
またよろしくお願いします。

閉鎖

“C言語何でも質問掲示板” へ戻る