2002-10-29 (Tue)
_ 値型と参照型
C#では値型と参照型がはっきり別れていてクラスのインスタンスは参照型なので スタックに置くことはできない。 一方、構造体は値型なのでスタックに置くことができる。また、メソッドで値型の 引数の内容を書き換えるために参照渡しも用意されている。
でも、値型と参照型の区別って本当に必要なんだろうか。C#くらい高級な言語では、 Rubyみたいに建前上は「ぜんぶ参照型ですよ」ということにしておいた方がずっと 分かりやすい気がする。GCもあるんだし。
本当にそういうものが必要ならその部分だけ他の言語(C++とか?)で書けばいい。 その方が.NET Frameworkのクロスランゲージというコンセプトに合っている 気がするんだけど。
2004-10-29 (Fri)
_ 出産
15時42分に産まれました。女の子。2826g。 母子ともに健康そうです。
[Matzにっき(2004-10-28)より引用]
おめでとうございます:)
講習会はどんちゃんにまかせとけばだいじょうぶですので、ごゆっくり。
_ refererspam.rb
refererspamのせいでシステムにかかる負荷が馬鹿にならないです。...前田さんのところに良さげなのがあったので導入してみました。
[大学生日誌(2004-10-28)より引用]
ごめんなさい、アクセスを拒否するわけではないので負荷は下がらないんじゃないかと...。
Refererを記録しないようにするので、その分の負荷は軽減できる*1かもしれませんが...。
*1 原理的にはキャッシュを返すだけでよい気がするけど、tDiaryのキャッシュの仕組みを知らなかったりして。
_ 無駄
Apache や、Ruby CGI 上でいくら対策しても CPU の無駄遣いのような気がしてならないんですよね。
[yamk日記(2004-10-13)より引用]
今のところ、referer spamでめちゃめちゃ負荷が高いといったこともないので、CPUの無駄遣いよりも、自分の労力の無駄遣いの方が気になっていたりします。 他所はひどいことになってたりするんですかねえ。
あ、うちのアクセスがそもそも少ないということか....。
_ スーパー牛さんパワー
aptitudeのへルプを見ると、以下のような意味不明の文が表示された。
excelsior:~$ aptitude --help|tail -1 aptitudeはスーパー牛さんパワーなど持っていません
原文は
excelsior:~$ LANG=C aptitude --help|tail -1 This aptitude does not have Super Cow Powers.
なのだけど、これってどういう意味なんだろう。
2005-10-29 (Sat)
_ 非決定性計算
今回いちばん面白かったのが、Haskell同好会のセッション。
吉田さんのプレゼンで非決定性計算の話が出て来たのだが、 Wikiでも紹介されていたようだ。
「他の言語じゃこんなことできないでしょ」という話だったが、 実はRubyConf2005のChad FowlerとJim Weirichのチュートリアルでも同じようなデモをやっていた。 それを使って書くと、
require "amb" A = Amb.new baker = A.choose(1, 2, 3, 4, 5) cooper = A.choose(1, 2, 3, 4, 5) fletcher = A.choose(1, 2, 3, 4, 5) miller = A.choose(1, 2, 3, 4, 5) smith = A.choose(1, 2, 3, 4, 5) A.assert([baker, cooper, fletcher, miller, smith].uniq.length == 5) A.assert(baker != 5) A.assert(cooper != 1) A.assert(fletcher != 1 && fletcher != 5) A.assert(miller > cooper) A.assert((smith - fletcher).abs != 1) A.assert((fletcher - cooper).abs != 1) p [baker, cooper, fletcher, miller, smith]
こんな感じ。 (Haskell版は全部の解が得られるけど、Ruby版は最初の解しか得られないところ がちょっと違う。)
どうやっているかというと、A.assertの呼びだしで継続を使ってバックトラック しているのだが、Rubyもなかなか面白いでしょ? ちなみに、amb.rbはこんな内容。
class Amb class ExhaustedError < RuntimeError; end def initialize @fail = proc { fail ExhaustedError, "amb tree exhausted" } end def choose(*choices) prev_fail = @fail callcc { |sk| choices.each { |choice| callcc { |fk| @fail = proc { @fail = prev_fail fk.call(:fail) } if choice.respond_to? :call sk.call(choice.call) else sk.call(choice) end } } @fail.call } end def failure choose end def assert(cond) failure unless cond end end
あとで、池上くんや山下さんとちょっと話したのだが、Haskell版はlazy なのがポイントらしい。 だからRubyでは無理でしょと言われて、その時はブロック使えばいいじゃん と話したのだが、継続版だとブロックも使わずにすっきり書けますね。
元ネタはSICPらしいけど、どんな解なんだろうな。 会社に行ったら調べてみよう。
追記:
リンク元のWikiページ を見ると、継続使うのはやっぱりSchemeからの借用っぽいですね。 そらそうだよなあ。
_ あんど [牛さんパワーは、 http://www.eeggs.com/items/36008.html という話があるそうです..]
_ smbd [mod_ruby環境でtdiaryを運用しているのなら負荷はそれほどかからないかと思いますが (ほとんどの人が層であ..]
_ shugo [なるほど! 勉強になります > 牛さんパワー]
_ shugo [なるほど! > mod_ruby みなさん、mod_rubyを使いましょう。 でもついこの間までCGIで運用してい..]