AOJでゴルフ

誤字脱字って恥ずかしいね!穴があったら入りたい気分。
それはさておき、AOJでゴルフするのに邪魔なreturnやexitですが、省ける時と省けない時があるみたい。
そもそもゴルフするところじゃないのかもしれませんが、できるんだったらやってみたくなる。
ということで、あまり検証はしてないのだけど現状分かってることだけメモ。
対象はVolume 0の0045 Sum and Averageです。
ついでに95Bのコードも。チートだけど。


追記
なんでreturnやexitを省略できるのか、どうしてそうなるのかichirin2501さんのところに書いてありました。
ebpやesp辺りの問題なのかなとか見当違いな考えをしてたのが恥ずかしいorz
パタヘネとか読み直そう。


追記の追記
ありがたいことに、わざわざ私のreturn不要のコードが何で動くのか、アセンブリコードも含めてincrementさんが解説して下さいました
感謝してもしきれないと同時に、自分の無知さが恥ずかしいよorz
return 0って書くと確かにeaxに即値で0を入れてる。なるほどなー
勉強になること、勉強することはまだまだたくさんある。


どうしてかわかった以上、以下の内容は役に立たないけど恥ずかしい思いをした記録として残しておきます。
Nyhxは教訓を手に入れた!


これは通らない。
0を返してないのでRuntime Error。

j, k, l, m;

main(i)
{
  for(; ~scanf("%d,%d", &i, &j); l += j, m++)
     k += i * j;
  printf("%d\n%d\n", k, l / m + 1);
}


exitを付ければ通る。

j, k, l, m;

main(i)
{
  for(; ~scanf("%d,%d", &i, &j); l += j, m++)
     k += i * j;
  printf("%d\n%d\n", k, l / m + 1);
  exit(0);
}


0は返していないけど通る。

j, k, l, m;

main(i)
{
  for(; i; l += j, m++)
    ~scanf("%d,%d", &i, &j) ? k += i * j : (i = !printf("%d\n%d\n", k, l / m + 1));
}

アセンブリコードを見てもなんで通るのかはさっぱり。知識が足りてないのもあるけど。
for文のループの継続条件を満たさなくなったら、leaveとretが実行されるラベルに飛んでるんだけどそのせい?
とはいえ、printfで終わってるコードもprintfをcallした後、すぐにleaveとretが実行されてるんだけどなあ・・・
とりあえずreturnとexitを省略したいなら、for文1個にコードを押し込めば通るっていうことがわかった。気がする。
そこまでしてもあんまり意味はないみたいだけど・・・
あー、何でかわかるようになりたい。