正木です。

In message "[ruby-dev:17762] Re: self in block"
 matz / ruby-lang.org (Yukihiro Matsumoto) writes:

|"initialize に {<x,...> ...} の形で与えられた block に対しては、
|その context を、initialize の中での context にする。
|
|よくわからないんですが、
|
|  Foo.new {<a,b,c>
|    ...
|  }
|
|の場合には、ブロック内部での
|
|  * selfはFooのインスタンス
|  * @fooはFooのインスタンス変数
|  * foo()はFooのメソッド呼び出し
|
|になるということでしょうか。とするとたとえば、

その通りです。ただし @foo はこの段階では未定義のはずですが。

|  @title = "widget title"
|  Foo.new {<>
|    set_title @title
|  }
|
|のようなものは動かないってことですよね。こういう場合には
|
|  @title = "widget title"
|  Foo.new {||
|    set_title @title
|  }
|
|としろということでしょうか。なんだか <> に複数の意味を与えて
|いるので混乱しそうな気がします。

なにが混乱するのか全然分かりません。
というより、上の script の意図が全く分かりません。
もしこれが、なにか別の class の method 定義のなかというのでなければ
  @title = "widget title"
の所で error になりそうですが?
ひょっとして
class Foo
  def initialize(title)
    @title=title
  end
end
Foo.new("widget title")
と同じことを block を使ってやりたいということですか?
いづれにしても <> を使うべき case ではなさそうです。

|それと
|
|  $SAFE=1 のときにはこの機能は使えない。

これは {<> ...} という構文は error にするという意味です。

さらに安全を期すために
"{<> ...} という構文の block 中に @ で始まる変数名があれば error にする"
を追加します。
これで
Foo.new{<> p @@foo}
のような情報漏洩に結び付きそうなものを排除できます。


|ってのは理由もよくわからないのですが


基本的に外部情報は大域変数と定数以外使えない仕様なので、security 上の
問題はないはずですが、新しい機能の追加が security hole になるのを心配
する人のための安全保証のつもりです。
 
|  @title = "widget title"
|  Foo.new {<>
|    set_title @title
|  }
|
|という同じプログラムが、$SAFEの値によって挙動が変化すること
|になると思うので、かなりまずい仕様だと思います。

問題の program は $SAFE の値の如何に関わらず error になります。

|私、正木さんが実現したいことがいまだによくわからないんですが。
|なにか読み落としているのでしょうか。


以前に書いたことの繰り返しになりますが、

次の
  def initialize
    @lambda=eval "lambda{"+yield+"}"
  end
を
  def initialize(&block)
    @lambda=block
  end

のようにすっきり書きたいということです。

要するに、原さんに
|しかし、lambda の上に eval までされると、いよいよ頭がぐちゃぐちゃ
|に、、、(^^;
と言われたくないということです。(勿論これは冗談です)

block を文字列で与える必要もなくなります。

いまは eval と文字列を利用して同等の機能を実現しているわけですが、
Proc については上の手法は使えない(initialize を書き換えるわけには
いかない)ため、新仕様で可能な

Proc.new{<n> n==0 ? 1:n*self[n-1]}

が現在はできません。



他の人にとっても、
自己参照もできる無名関数が簡単にできるというだけでも非常に有用だ
と思います。
それとひきかえに失うものが、実装するための苦労も含めて非常に大きく、
しかもそれに対する対策もないということを示していただければ、私の
提案はすぐに取り下げます。