MEL合宿 -13日目-は、最初の頃はハマってしまう「if文での変数での扱い」について見ていきたいと思います!(`・ω・´)ゞ
if文で変数を作ると、、、
MEL合宿 -12日目-で作成した、フレームレートのコードで実験してみたいと思います。
string $timeUnit = `currentUnit -q -time`; if($timeUnit == "film"){ print "FPS is 24."; }else if($timeUnit == "ntsc"){ print "FPS is 30."; }else if($timeUnit == "ntscf"){ print "FPS is 60."; }else{ error "FPS is unknown."; }
こちらのメッセージの出力で、同じようなメッセージを何度も書いています。もし、「英語が間違えていた」「メッセージのフォーマットを変えたい」という時に修正箇所が多いので、変数をうまく使ってみようと、以下のように修正してみます。
string $timeUnit = `currentUnit -q -time`; if($timeUnit == "film"){ string $fps = "24"; }else if($timeUnit == "ntsc"){ string $fps = "30"; }else if($timeUnit == "ntscf"){ string $fps = "60"; }else{ string $fps = "unknown"; } print ("FPS is" + $fps + ".");
if文でメッセージの変わる部分だけを作って、最後に文字列を連結してメッセージを組み立てる、、、合理的ですね(*´ω`*)
こちらを実行してみると、、、
「“$fps” is an undeclared variable.」
え、、、?
“$ fps”は宣言されていない変数です。!?
変数「$fps」は、ちゃんとif文の中で作っているにも関わらず、if文の外に書いた「print」で変数を使おうと思うと、エラーしてしまいました。
これは、「スコープ」というものが関わってきます(;・∀・)
スコープって?
実は、MELの変数には「使える範囲」が決まっていて、これを「スコープ」と言います。「{}」で囲まれた中で宣言された変数は、その中でしか使えません。(´・ω・`)
なので、先程の変数「$fps」は、if、else if、elseのそれぞれの中でしか使えない変数なので、外に書いたprintでは使えないっということになります。
「{}」の内側に書かれた変数を「ローカル変数」と言います。逆にどの「{}」にも属さない変数を「グローバル変数」と言います。
どうすればいいの!?
先程の例では、「変数の宣言だけする」のがキーになります。覚えていますか!?「MEL合宿 -5日目-」でちょっと登場しました(`・ω・´)ゞ
string $timeUnit = `currentUnit -q -time`; string $fps; if($timeUnit == "film"){ $fps = "24"; }else if($timeUnit == "ntsc"){ $fps = "30"; }else if($timeUnit == "ntscf"){ $fps = "60"; }else{ $fps = "unknown"; } print ("FPS is" + $fps + ".");
2行目に書いた「string $fps;」で変数を宣言だけしたので、if文の外に書いた「print」でも使用することができます!状況に応じて代入する値を変えたい場合は、このような形にするといいと思います(*´ω`*)
グローバル変数は注意が必要!
実は、上記のコードは「{}」で囲われていないので、そのままScript Editorで作業してしまうと「グローバル変数」になってしまいます。
グローバル変数の何が注意かといいますと、、、「どこからでも使える変数」というところにあります。一見便利じゃんっと思うかもしれませんが、トラップ満載なのです∠( ゚д゚)/
他のMELにも影響する
どこからでも使えるので、自分のMELだけでなく、他のMELからも使えることができます。自分のツールで使っている変数が変なタイミングで書き換えられて不具合を起こす可能性があります。
変数名の重複
MELは、同じ名前の変数は作るこはできません。先程の変数「string型の$fps」がありますが、Script Editorで「int型の$fps」を作ろうとしても、既に変数が作られているのでエラーしてしまいます。自分のツールと同じ名前のグローバル変数を使うツールが合った場合、どちらかのツールがうまく動作しなくなる可能性が大いにあります。
厄介なことに、グローバル変数はMayaを終了するまで消えません。
実験的なコードを作りたい場合は
上記のコードのように、実験的なコードや、勉強用のコード、使い捨てのツールなどを作る場合は、以下の様に「コード全体を{}で囲う」ようにしてあげると気づきにくいトラブルを回避することができます。
{ string $timeUnit = `currentUnit -q -time`; string $fps; if($timeUnit == "film"){ $fps = "24"; }else if($timeUnit == "ntsc"){ $fps = "30"; }else if($timeUnit == "ntscf"){ $fps = "60"; }else{ $fps = "unknown"; } print ("FPS is" + $fps + "."); }
今後やる項目でも、スコープは大切な要素なので、今のうちに頭に叩き込んでおいてください(`・ω・´)ゞ
まとめ!
- 変数は使える範囲が決まっていて、範囲のことを「スコープ」という!
- 「{}」の中の変数を「ローカル変数」という!
- 「{}」の外の変数を「グローバル変数」という!
- グローバル変数は色々厄介!
- 実験的なコードでも「{}」で囲うと、トラブル回避しやすい!
それでは次回もお楽しみに!(`・ω・´)ゞ