関数型プログラミングのために純粋に設計されたCPUはどう違うのでしょうか?


14

CPUは、人々が暗黙的または明示的に作成するソフトウェアを念頭に置いて設計されています。

命令セットアーキテクチャの設計を見ると、各命令が命令型コマンドをエンコードするという意味で、それらは非常に「命令型」であるように思えます。また、現在の命令セットアーキテクチャは、プログラマが生成するコードのタイプに部分的に基づいて進化しているようにも思えます。

関数型プログラミングスタイルで記述されたプログラムのみを実行することを知って、CPUをゼロから設計する場合、そのCPUは既存のCPUとは異なるようにどのように設計されますか?


9
ジョン・バッカスの「プログラミングはフォン・ノイマン様式から解放されますか?」そのような作品についてはほとんど言及していません(セクション15)。
ドミトリアーバノビッツ

(グラフ)リダクションマシンを探すか、W。Klugeの絶版の書籍The Organization of Reduction、Data Flow、and Control Flow Systems(MIT Press、1992)のコピーを探して、地元の研究図書館にアクセスしてください。
カイ

2
また、Koopmanの著書「Combinator Graph Reductionのアーキテクチャ(AP、1990)」。Lispマシンを調べることもおそらく価値があります。en.wikipedia.org/wiki/Lisp_machine
仮名

基本的に、マシンは時間とともに実行され、状態が変化するため、常に不可欠だと思います。
orlp

いくつかの便利なCPU機能は、サンクのネイティブサポートとより効率的なジャンプです。また、CPUは、メモリ内の特定の場所が特定のスコープで上書きされないことを知って、CPUがスタックベースの言語と同じ方法でスタックを維持する必要がないことを知って、いくつかのショートカットを取ることができます。
モニカの復活

回答:


2

実際には、それが行われています:https : //en.wikipedia.org/wiki/Lisp_machine

FPのCPU設計の1つの側面は、ガベージコレクションです。GCは関数型言語にとって非常に重要です。一般的な実装では、GCがポインターデータと非ポインターデータを区別できる必要があります。事実上、それはデータに沿って余分なビットを保存することを意味します。これが、たとえば、OCaml整数が32ビットアーキテクチャで31ビット、64ビットアーキテクチャで63ビットだけである理由です。整数演算には、厄介な余分なシフト演算が含まれます。他の言語(または他のOCamlデータ型)は、その余分なビットのためにマシン語全体を浪費し、64ビット整数に128ビットを使用する場合があります。GC向けにネイティブに設計されたCPUには、65ビットのデータバスがありますが、64ビットの算術演算があります。

ただし、多くの非機能言語にもガベージコレクションがあり、それぞれのアーキテクチャから利益を得ます。

頭に浮かぶもう1つのことは、FPのメモリ使用量は通常、命令型プログラムのメモリ使用量よりはるかに分散していることです。これは主に、配列を使用するのが自然ではないためです。その結果、これらのプログラムは、連続したメモリチャンクをキャッシュすることによる利益が少なくなります。そのため、FP CPUは異なるキャッシュ戦略を使用する場合があります。


1

それは何も変更しないか、Reduceronとその後続のPilGRIM 1のような大規模な並列設定を利用します1巨大なスタックでます。

最初は何も変わらないという声明は大胆に思えますが、CPUはシーケンシャルなので、利用可能なハードウェアを使用して効率を拡張する変換プロセス(コンパイル)があります。別のアーキテクチャがあるとすれば、一部の操作はより高速になり、一部は高速化するためにハッキングのトリックが必要になります。

違いを生むアーキテクチャーでは、マップ操作とリストをより速く実行する必要があります(ストーリー全体ではなく、効果を示すのに十分です)。リストをネイティブに実行する動的に変化するハードウェアを作成する可能性はないため、これらは連続したメモリに格納されます。何らかの形式の配列表現に固執します。マップの場合、非シーケンシャル設定で実行するには-Reduceronに戻ります。そのため、連続した命令に対して効果的に1つの中央処理を行い、並列処理をサポートします。

異なる可能性があるのは、複数の関数をロードしてフレームジャグリングなしで実行する可能性です。ただし、関数に複数のユニットを追加すると、メモリへのアクセスに混乱が生じます。

kneの答えに加えて、GCはコプロセッサーとして実行するのに有益であり、非常に便利な機能です。

1:PilGRIMについては、Boeijink A.、HölzenspiesPKF、Kuper J.(2011)PilGRIMの紹介:遅延関数型言語を実行するためのプロセッサで適切に説明されていますIn:Hage J.、MorazánMT(eds)実装および関数型言語の適用。IFL2010。コンピューターサイエンスの講義ノート、第6647巻。Springer、ベルリン、ハイデルベルク


「再帰をネイティブにする可能性はありません」。これがなぜなのか説明してもらえますか?最初は驚きました。
user56834

また、reduceronはfpgaで実行するのではなく、ハードCPUになる可能性がありますか?
user56834

私の悪い、私はネイティブ再帰を意味しましたが、それはプロバルビーとは無関係です。少し修正する必要があります。

0

最初にちょっとした冗談:100%機能的なプログラムを実行しても何も有用なことはできないので、NOP命令だけで十分です。(私はこれを炎戦争のために開きます)。

そのため、IOの命令型命令と命令型プログラミングの通常のサポートが必要になります。

それ以外の場合、使用される実際の言語に一部依存します。私の頭の上の2つはHaskellとErlangです。

Haskellはリストとマップのサポートから恩恵を受けると信じています。リストは特定のハードウェアメモリマッピングでサポートされ、リンクされたリストを連続したアドレスセットに変換できます。最初の要素はアドレスnにあり、2番目の要素はアドレスn + 1にあります。リストから最初の要素を削除するには、ポインタnを変更するだけです。最後に、nポインターを削除すると、すべてのメモリーが解放されます。マップは連想配列としてサポートできます。検索値を入力すると、メモリシステムがアイテムを返します。繰り返し検索する必要はありません。

Erlangは、メッセージ/プロセスのサポートと完全な状態での末尾再帰の恩恵を受ける可能性があります。メッセージとプロセスはさまざまな方法でサポートできます。1つの例は、非常に大量の処理コアを持つことです。テールの再帰は、メモリコントローラーが状態をはるかに高速にコピーできることを認識して改善できます。おそらく、大量のデータをコピーするのではなく、メモリシステムポインターを変更するだけです。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.