投稿
ネタバレ
おにぎり EasyPuzzler65
ややこしい話なのでネタバレ扱いにします。次のコメントで詳しく説明します。
3そうだね
プレイ済み
返信[1]
親投稿
おにぎり EasyPuzzler65
defコマンドを使うと自分だけのコマンドが作れてかっこいいですが、outのあとに書ける変数って、いきなり読もうとするとエラーになってしまうのが不便だなあと。最初の画像のプログラムの例は、xy座標が画面の範囲に収まるようにクリッピングするような命令を想像して見ていただけるとしっくりくると思います。本当はclippingerrのように書きたいのですが、エラーになってしまいます。確かどなたかが同じ話を議論されていたように思うのですがうまく探せませんでした。
3そうだね
プレイ済み
返信[2]
親投稿
ゆうたん yu-tan-sama
えーと defで定義された部分とそうじゃない部分はメモリ空間が切り離されています なので、呼び出し元のPという変数と、def内のAAやAという変数は厳密には別の変数です 呼び出し時にPの内容がAAにコピーされ、戻るときにAの内容をPにコピーするって認識しておくといいかもしれません こんな説明でいいのかな?
0そうだね
プレイ済み
返信[3]
親投稿
おにぎり EasyPuzzler65
outの後の変数のほうにも最初にコピーしておいてくれればいいと思うんだけど、そうなっていないのが残念だなあ、ということです。
0そうだね
プレイ済み
返信[4]
親投稿
推測なので間違っていたら申し訳ありません。 4行目をIF - ENDIFの形式にして複数行にすると IF A<3 THEN の行でエラーになっています。 Aに値を代入する前に評価しているためにエラーになっています。AはOUT引数なので、呼び出し元のPとは別物で、戻るときにAの値をPに代入する動作をプチコンはしているはずです。
0そうだね
プレイ済み
返信[5]
親投稿
以下のようにしても同様の意味になるかと思います。 DEF CLIPPING A OUT AA IF A<3 THEN AA=3 IF A>7 THEN AA=7 END
0そうだね
プレイ済み
返信[6]
親投稿
スー thanks_0u0
私もDEFはよくわからない派なので、お勉強がてら…。 スクショのようにすればちょっと見映えが良いかもしれません。 私の理解では、OUTの後はあくまで処理結果を返すための変数であって、ユーザー命令に渡すための変数ではないから、DEF~~ OUT ○、だと計算するための材料がないのかな、と思っています。 また、見た目は悪いですけれど、数値の丸めはMAX,MINでもできますよ(・ω・)ノ
0そうだね
プレイ済み
返信[7]
親投稿
けい kei0baisoku
私が見た中だと、全く同じ話題は無かったと思います。 関数の一行目で A=A ができないという事ですよね?空状態で初期化されてるからと考えれば辻褄は合いそうですが、確かに意外です。 ちなみに私は同じものを DEF CLAMP(X,MIN,MAX) と関数形式で作ったので、この問題には気付きませんでした。
0そうだね
プレイ済み
返信[8]
親投稿
ゆうたん yu-tan-sama
OUT側に指定する変数って未初期化の可能性があるから原則使えない物だと思うのです 他の言語の一般的な実装だと、IN側の値を加工して返せるような宣言や手段が用意されてる感じですかねぇ もっとも、その手の実装に頼ると、壊しちゃいけない変数を渡してしまってバグるとかそういう事故があるので…
0そうだね
プレイ済み
返信[9]
親投稿
おにぎり EasyPuzzler65
最初に変数名がテキストに表われたときに初期化してなくて、代入が発生したときに初めて初期化しているからそうなるのもしれないですね。
0そうだね
プレイ済み
返信[10]
親投稿
グローバルな変数はメモリ割り付け時に、初期化するエリアとしないエリアをきめ、ローカルエリアはスタックに割り当てるため初期化しないという習慣を、踏襲したのではないでしょうか。
0そうだね
プレイ済み
返信[11]
親投稿
おにぎり EasyPuzzler65
このことに気がついた実際のプログラム例を別スレッドにしました。うーん、その説だと、DEFの実行が終わって本線に戻るとき、わざわざグローバル変数側のメモリにコピーする操作が必要ですよね。呼び出す側で確保したメモリのポインタをDEF側に渡すようにしておけば避けられるコピーです。ああ、問題は配列ですかね。でも配列ってOUT以下に書けないんでしょ? 配列はOUTの前に書いて変数渡しになるよ、って、どなたかのまとめサイトにありました。
0そうだね
プレイ済み
返信[12]
親投稿
配列は参照渡しになるので、配列要素はINOUTのように扱えます。
0そうだね
プレイ済み
返信[13]
親投稿
おにぎり EasyPuzzler65
配列を使うのはトリッキーですが案外筋がいいかもしれないですね。みなさんコメント感謝です。
0そうだね
プレイ済み
返信[14]
親投稿
スー thanks_0u0
私も気になったので色々試してみたのですが、私のおつむではやっぱり配列で渡すしかないのかなぁ、という感じでした(u_u) 配列にするとDEF以外で使うときの見た目がよろしくない気もします。 関数にして、XYで分けるか、けいさんのようにMINMAXを入れられるものを使う、というのも完全にスッキリとは言えなさそうで、現状の機能ではどこかに妥協が必要かもです…。 望み薄ですが、もしかしたらDEF内からのRESTOREのようにプチコンの仕様を改良してくれることもあるかもしれませんし、公式さんに意見を伝えてみるのも良いのかもしれませんね。
0そうだね
プレイ済み
返信[15]
親投稿
おにぎり EasyPuzzler65
out以下は出力オンリーね、というのもポリシーとしてありかな、とおもいますが、仕様としてはっきりさせてください、というお願いはしていいのかな。。。
0そうだね
プレイ済み
返信[16]
親投稿
スー thanks_0u0
ツイッターで小林社長とユーザーさんがやりとりしているのはよく見かけますので、意見はきちんと聞いていただけると思いますし、質問すれば回答もおそらくいただけると思いますよ( ´▽`)
0そうだね
プレイ済み
返信[17]
親投稿
けい kei0baisoku
なるほど、少なくともポリシーがはっきりすれば混乱は抑えられそうですね。
0そうだね
プレイ済み
返信[18]
親投稿
おにぎり EasyPuzzler65
プチコンのWebサイトから質問を投稿してみました。もしお返事がいただけたらまたご報告します。
1そうだね
プレイ済み
返信[19]
親投稿
てらこや actorbug
グローバル変数限定になりますが、こんな方法もあります。
0そうだね
プレイ済み
返信[20]
親投稿
けい kei0baisoku
VARって変数参照にも使えたんですか!?(°Д°) これは使えます!
0そうだね
プレイ済み
返信[21]
親投稿
おにぎり EasyPuzzler65
ひえー、マニュアルに載ってないのにどうやって見つけたんだろ!サンプルプログラムに潜んでいるのかな…しかしおみごとです.
0そうだね
プレイ済み
返信[22]
親投稿
セキュリティ上の欠陥になりませんか?
0そうだね
プレイ済み
返信[23]
親投稿
スー thanks_0u0
ほぇ〜、すごいですね!(゚o゚;; やってみたら本当に出来ちゃいました。 引数が2つ以上あっても綺麗に書けますし、これがヘルプに載っていない仕様とかなら、かなり使えるのでは…!
0そうだね
プレイ済み
返信[24]
親投稿
てらこや actorbug
サンプルのSYS/SBMAPで使われていた方法なので、多分使っても大丈夫だと思います。
0そうだね
プレイ済み
返信[25]
親投稿
けい kei0baisoku
CHKVARがあるので、CALLの変数版みたいなのもあるんじゃないかと思ってちょうど今日探したのですが………サンプルにあったとは。 一度すみずみまで目を通した方がいいかなぁ。
0そうだね
プレイ済み
返信[26]
親投稿
ありがたく、使わせていただきます。
0そうだね
プレイ済み
返信[27]
親投稿
おにぎり EasyPuzzler65
やあ本当だー!1000行以上あるプログラムにきっちり目を通しておられるわけね…脱帽。
0そうだね
プレイ済み
返信[28]
親投稿
てらこや actorbug
ただ、同じ名前のローカル変数があると、そちらを参照してしまうのでご注意ください。 ちなみに、この機能は偶然発見したものなので、サンプルにきっちり目を通しているわけではありません。
0そうだね
プレイ済み