質問

Schemeは、関数または他のタイプの値にバインドされているかどうかに関係なく、すべての変数に単一の名前空間を使用します。 Common Lispはこの2つを分離するため、識別子「hello」はあるコンテキストの関数と別のコンテキストの文字列を参照する場合があります。

(注1:この質問には上記の例を必要とします。自由に編集して追加するか、元の作者にメールで送ってください。)

ただし、他の関数にパラメーターとして関数を渡すなど、一部のコンテキストでは、プログラマーは、# 'を使用して、非関数変数ではなく関数変数を指定していることを明示的に区別する必要があります、次のように:

(sort (list '(9 A) '(3 B) '(4 C)) #'< :key #'first)

私はこれを少しいぼだと思っていましたが、最近引数はこれが実際に機能であること

... 重要な違いは、実際にはフォームの構文ではなく、 オブジェクトのタイプ。ランタイム値について何も知らずに 関与していることは、関数形式の最初の要素が 関数でなければなりません。 CLはこの事実を取り入れて、 言語、およびマクロと特殊形式も使用可能(および必須) 静的に決定されます。だから私の質問は:なぜあなたは 同じ名前になる関数の名前と変数の名前 関数名の主な用途が 変数名はめったに表示されませんか?
クラス名の場合を考えてください:なぜFOOという名前のクラスが防ぐべきなのか FOOという名前の変数の使用?私が言及している唯一の時間 FOOという名前のクラスは、クラス名を期待するコンテキストにあります。もし、 まれに、にバインドされているクラスオブジェクトを取得する必要があります クラス名FOO、FIND-CLASSがあります。

この議論は、経験から私にはある程度意味があります。 Haskellには、フィールドにアクセスするために使用される関数でもあるフィールド名を使用した同様のケースがあります。これは少し厄介です:

data Point = Point { x, y :: Double {- lots of other fields as well --} }
isOrigin p = (x p == 0) && (y p == 0)

これは、 NamedFieldPuns 拡張機能によって特に優れた追加の構文によって解決されます。

isOrigin2 Point{x,y} = (x == 0) && (y == 0)

それでは、質問に対して、一貫性を超えて、Common LispとSchemeの両方の利点と欠点は何ですか?一般に、すべての値の単一の名前空間と関数と非関数値の別々の名前空間の両方について

役に立ちましたか?

解決

2つの異なるアプローチには、Lisp-1とLisp-2という名前があります。 Lisp-1には変数と関数の両方に単一の名前空間があり(Schemeのように)、Lisp-2には変数と関数に別々の名前空間があります(Common Lispのように)。あなたが質問でそれを参照しなかったので、用語を知らないかもしれないので、私はこれに言及します。

Wikipedia この議論を参照

  

関数の個別の名前空間が利点であるかどうかは、Lispコミュニティでの競合の原因です。通常、Lisp-1対Lisp-2の議論と呼ばれます。 Lisp-1はSchemeのモデルを指し、Lisp-2はCommon Lispのモデルを指します。これらの名前は、リチャードP.ガブリエルとケントピットマンによる1988年の論文で造られ、2つのアプローチを大まかに比較しています。

機能セルと値セルの分離の技術的な問題というタイトルのガブリエルとピットマンの論文はまさにこの問題に対処します。

他のヒント

実際、リチャードガブリエルとケントピットマンの論文で概説されているように、議論はLisp-6に対するLisp-5は、他にもいくつかの名前空間が既に存在するため、論文では型名、タグ名、ブロック名、宣言名に言及しています。編集:Rainerがコメントで指摘しているように、これは間違っているようです:Schemeは実際にはLisp-1のようです。ただし、以下はこのエラーの影響をほとんど受けません。

シンボルは、実行するものを示すか、参照するものをコンテキストから常に明確にします。関数と変数を同じ名前空間にスローすることは、主に制限です。プログラマーは、モノとアクションに同じ名前を使用することはできません。 Lisp-5がこれから得られるのは、現在のコンテキストが意味するものとは異なる名前空間から何かを参照するための構文上のオーバーヘッドが回避されるだけです。編集:これは全体像ではなく、表面のみです。

Lisp-5の支持者は、関数がデータであるという事実を好み、これは言語コアで表現されることを知っています。リスト「リスト」を呼び出すことができるという事実が好きです。車「車」コンパイラを混乱させることなく、関数は基本的に特別な種類のデータです。編集:これが私の主要なポイントです:個別の名前空間はいぼではありません。

Pascal Constanzaの機能これについて言ってください。

Python(名前空間の統一)対Ruby(メソッドとメソッド以外の明確な名前空間)で同様の区別に出会いました。その文脈では、私はPythonのアプローチを好みます-例えば、そのアプローチでは、物のリストを作りたい場合、その一部は機能であり、他はそうではないので、私はそれらの名前で異なることをする必要はありません、たとえば「機能性」に応じて。同様の考慮事項は、関数オブジェクトが呼び出されるのではなく周囲にバンディングされるすべてのケースに適用されます(高階関数への引数、および高次関数からの戻り値など)。

非関数も呼び出すことができます(Pythonの場合、クラスが __ call __ を定義している場合-&quot; operator overloading&quot;の特殊なケース)。したがって、「コンテキストの区別」は必ずしも明確でもありません。

しかし、私の「lisp-oid」は経験は主にCommon LispではなくSchemeである/だったので、最終的にその経験に由来する均一な名前空間に精通していることに無意識に偏っているかもしれません。

Schemeの関数の名前は、その値として関数を持つ変数です。 (define x(y)(zy))または(let((x(lambda(y)(zy))))を行うかどうか、だから、「変数名はめったにそこに現れたくない」という考えは、Schemeに関しては一種のスペシャリストです。

Schemeは特徴的な関数型言語であるため、関数をデータとして扱うことはその原則の1つです。関数を他のすべてのデータのように保存される独自のタイプにすることは、アイデアを引き継ぐ方法です。

少なくともCommon Lispにとって、私が見る最大の欠点は理解可能性です。変数と関数に異なる名前空間を使用していることに全員が同意できますが、いくつありますか? PAIPで、Norvigは「少なくとも7」を持っていることを示しました;名前空間。

著名なプログラマーによって書かれた言語の古典的な本の1つが出版された本の中で確実に言えない場合、問題があると思います。複数の名前空間に問題はありませんが、少なくとも、誰かがこの側面を完全に理解できるように、言語が十分にシンプルであることを望みます。

変数と関数に同じシンボルを使用するのは問題ありませんが、より曖昧な領域では、恐れて異なる名前を使用することに頼ります(名前空間の衝突はデバッグするのが本当に難しいかもしれません!)決してそうではありません。

両方のアプローチには良いことがあります。ただし、重要な場合は、関数LISTと変数LISTの両方を誤って入力するよりも、両方を使用する方が好ましいことがわかりました。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top