タグ付けされた質問 「immutability」

2
すべての主要なOOP機能を失うことなく、OOPで不変性を本当に使用できますか?
私のプログラムでオブジェクトを不変にすることの利点を理解しています。アプリケーションの良い設計について本当に深く考えているとき、私は多くの場合、オブジェクトの多くが不変であることに自然に到達します。多くの場合、すべてのオブジェクトを不変にしたいところになります。 この質問は同じ考えを扱っていますが、不変性に対する優れたアプローチと、それを実際に使用するタイミングを示唆する答えはありません。いくつかの良い不変のデザインパターンがありますか?一般的な考え方は、「オブジェクトを変更する必要が絶対にない限り、オブジェクトを不変にする」ことであるように見えますが、実際には役に立ちません。 私の経験では、不変性はコードをますます機能的なパラダイムに追い込み、この進行は常に起こります。 リスト、マップなどの永続的な(機能的な意味での)データ構造が必要になります。 相互参照(たとえば、子が親を参照している間、子を参照しているツリーノード)で作業することは非常に不便です。 継承は意味をなさないために停止し、代わりに構成を使用し始めます。 カプセル化のようなOOPの基本的な考え方全体がバラバラになり始め、私のオブジェクトは関数のように見え始めます。 この時点で、私は実際にはOOPパラダイムの何も使用しておらず、純粋に機能的な言語に切り替えることができます。したがって、私の質問:良い不変のOOP設計への一貫したアプローチがありますか、または不変のアイデアを最大限に活用すると、常にOOPの世界から何も必要としない関数型言語でプログラミングすることになりますか?OOPがバラバラにならないように、どのクラスを不変にし、どのクラスを不変にするかを決定するための良いガイドラインはありますか? 便宜上、例を示します。さんが持ってみましょうChessBoard不変のチェスの駒の不変なコレクションとして(抽象クラスを拡張しますPiece)。OOPの観点から見ると、ピースはボード上の位置から有効な動きを生成する役割を果たします。しかし、動きを生成するには、ピースがそのボードへの参照を必要とする一方で、ボードはそのピースへの参照を必要とします。さて、あなたのOOP言語に応じてこれらの不変の相互参照を作成するためのいくつかのトリックがありますが、それらは管理するのが苦痛で、ボードを参照する部分を持たない方が良いです。しかし、ボードの状態がわからないため、ピースは動きを生成できません。すると、ピースはピースタイプとその位置を保持する単なるデータ構造になります。その後、ポリモーフィック関数を使用して、あらゆる種類のピースの動きを生成できます。これは関数型プログラミングでは完全に達成できますが、ランタイム型チェックやその他の不適切なOOPプラクティスがないOOPではほとんど不可能です...

2
不変データを持つ言語で二重にリンクされたデータ構造または循環データ構造に操作を実装するための回避策
Haskellでグラフを作成してローカル操作を行う方法を学びたいのですが、問題はHaskellに固有のものではなく、グラフの代わりに二重リンクリストを検討することもできます。 質問: 主に不変のデータ構造(Haskell、Clojureなど)をサポートおよび推奨する言語で、二重リンクリスト(または他の二重リンクまたは循環データ構造)とその操作を実装する慣用的または推奨される方法は何ですか? ?特に、言語で正式に禁止されているインプレース更新の使用方法は? 二重にリンクされたリストでローカル操作を実行した場合(アイテムが挿入された場合など)、言語の遅延により、リスト全体をすぐにコピーする必要がない場合があることは容易に想像できます。ただし、リストは二重にリンクされているため、1か所で変更された場合、リストの新しいバージョンで古いノードを使用することはできず、何らかの方法でマーク、コピー、ガベージコレクションを行う必要があります。 。リストの更新されたコピーのみを使用する場合、これらは明らかに冗長な操作ですが、リストのサイズに比例した「オーバーヘッド」が追加されます。 これは、そのようなタスクでは不変データが単に不適切であり、可変データを「ネイティブ」でサポートしていない関数型宣言言語は、命令型言語ほど優れていないことを意味しますか?または、トリッキーな回避策はありますか? PS私はインターネットでこの主題に関するいくつかの記事やプレゼンテーションを見つけましたが、それらをフォローするのに苦労しましたが、この質問への答えは1段落以上、そしておそらく図を取るべきではないと思います...つまり、もしあればこの問題に対する「機能的な」解決策はありません。答えは「Cを使用する」でしょう。ある場合、それはどれほど複雑になる可能性がありますか? 関連する質問 「関数型プログラミングのデータ構造」。非効率的な代替手段の代わりにインプレース更新を使用することについての私の特定の質問はそこでは議論されていません。 「永続的データ構造の内部変異」。ここでは、不特定の言語での低レベルの実装に重点が置かれているようですが、私の質問は、言語(関数型またはその他)の正しい選択と、関数型言語で可能な慣用的な解決策についてです。 関連する引用 純粋に関数型のプログラミング言語では、多くのアルゴリズムを非常に簡潔に表現できますが、その場で更新可能な状態が重要な役割を果たすと思われるアルゴリズムがいくつかあります。これらのアルゴリズムの場合、更新可能な状態がない純粋に関数型の言語は本質的に非効率的であるように見えます([Ponder、McGeer and Ng、1988])。 -John LaunchburyおよびSimon Peyton Jones、レイジー機能状態スレッド(1994)、John LaunchburyおよびSimon Peyton Jones、Haskell州(1995)。これらの論文STでは、Haskellのモナディック型コンストラクタを紹介しています。

4
不変性を保証することは、プロパティではなくフィールドを公開する正当な理由ですか?
C#の一般的なガイダンスは、常にパブリックフィールドではなくプロパティを使用することです。これは理にかなっています。フィールドを公開することで、実装の詳細の多くを公開することになります。プロパティを使用すると、その詳細をカプセル化して、コードを消費しないようにし、実装の変更をインターフェイスの変更から切り離します。 ただし、readonlyキーワードを処理するときに、このルールに有効な例外が時々あるかどうか疑問に思っています。このキーワードをパブリックフィールドに適用すると、不変性が保証されます。これは単なる実装の詳細ではなく、不変性は消費者が関心を持つ可能性のあるものです。readonlyフィールドを使用すると、フィールドがパブリックコントラクトの一部になり、パブリックインターフェースを変更することなく、将来の変更または継承によって破壊されないものになります。プロパティが提供できないものです。 それでは、不変性を保証することが、readonly場合によってはプロパティよりもフィールドを選択する正当な理由でしょうか? (明確にするために、クラスの設計の一部として意味があり、契約に不変性を含めることが意図されている場合にのみ、現時点でフィールドが不変であるという理由だけで、常にこの選択を行うべきだと言っているわけではありません。私は主に、メンバーがにある必要があるinterface場合や遅延読み込みを行う場合など、正当化できない特定のケースではなく、これが正当化されるかどうかに焦点を当てた回答に関心があります。)

6
オブジェクトが可変である場合、関数型プログラミングのコンテキストで何が問題になる可能性がありますか?
不変オブジェクトのような可変オブジェクトと不変オブジェクトの利点は、共有および書き込み可能な状態が原因で、マルチスレッドプログラミングの問題のトラブルシューティングが非常に困難になることを理解できます。逆に、変更可能なオブジェクトは、毎回新しいコピーを作成するのではなく、オブジェクトのIDを処理するのに役立ちます。そのため、特に大きなオブジェクトのパフォーマンスとメモリ使用量も向上します。 私が理解しようとしていることの1つは、関数型プログラミングのコンテキストで可変オブジェクトを使用すると何が問題になるのかということです。私に言われたポイントの1つのように、異なる順序で関数を呼び出した結果は確定的ではありません。 関数プログラミングで可変オブジェクトを使用すると何がうまくいかないかが非常に明白な実際の具体例を探しています。基本的にそれが悪いのであれば、オブジェクト指向や関数型プログラミングのパラダイムに関係なく悪いのですよね? 私自身の声明自体がこの質問に答えると思います。それでももっと自然に感じられるように、いくつかの例が必要です。 OOは、カプセル化、ポリモーフィズムなどのツールを使用して、依存関係を管理し、より簡単で保守可能なプログラムを作成するのに役立ちます。 関数型プログラミングも、保守可能なコードを促進する同じ動機がありますが、OOツールとテクニックを使用する必要性を排除するスタイルを使用しています。

2
Haskell / Clojureは、実際には粒子シミュレーションなどの動的システムには適していませんか?
以前の質問で、関数型プログラミング言語は物理エンジンなどの動的システムには適していないと言われています。これは、主にオブジェクトの変更にコストがかかるためです。このステートメントはどの程度現実的ですか、そしてその理由は何ですか

3
不変の構造と深い構成階層
私はGUIアプリケーションを開発しています。グラフィックを多用しています。例として、ベクターエディターと考えることができます。すべてのデータ構造を不変にするのは非常に魅力的です。そのため、ほとんど労力をかけずに、元に戻す/やり直し、コピー/貼り付け、その他多くのことを行うことができました。 簡単にするために、次の例を使用します。アプリケーションを使用して多角形を編集するため、「不変点」の単なるリストである「Polygon」オブジェクトがあります。 Scene -> Polygon -> Point そして、私はプログラムに1つだけの可変変数があります-現在のシーンオブジェクトを保持する変数です。私が抱えている問題は、ポイントドラッグを実装しようとしたときに発生します。可変バージョンでは、Pointオブジェクトを取得してその座標の変更を開始するだけです。不変バージョン-行き詰まっています。PolygoncurrentのSceneインデックス、にドラッグされたポイントのインデックスを格納しPolygon、毎回それを置き換えることができます。しかし、このアプローチはスケーリングしません。構成レベルが5に達すると、ボイラープレートは耐えられなくなります。 この問題は解決できると確信しています-結局のところ、完全に不変の構造とIOモナドを持つHas​​kellがあります。しかし、私はその方法を見つけることができません。 ヒントをください。

3
特に明記しない限り、C ++のすべてのオブジェクトは変更可能ですか?
特に明記しない限り、C ++のすべてのオブジェクトは変更可能ですか? PythonとJavaScriptでは、文字列、タプル、ユニコードを変更できません。C ++に不変なものがあるかどうか、またはすべてのオブジェクトが変更可能であるかどうかを疑問に思っていましたconst。不変にするために型修飾子を使用する必要があります。

3
オブジェクトの同一性と可変性
私はJavaの値型の提案を読んでいて、この文に出くわしました。「オブジェクトIDは可変性をサポートするためだけに機能し、オブジェクトの状態は変更できますが、同じ組み込みオブジェクトのままです。」 (仮にではあるが)私が理解していることから、オブジェクトIDは、変数がメモリ内の他の場所にあるオブジェクト(JavaまたはC#のヒープでインスタンス化されたオブジェクトなど)へのポインタまたは参照として機能するという考えです。では、これはオブジェクトの可変性とどう関係しているのでしょうか?これは、たとえば、C ++でスタックにインスタンス化されたオブジェクトが不変であることを意味しますか?ここのリンクが表示されません。

4
C#デリゲートは不変ですが、なぜそれが重要なのですか?
これは、この他の質問のフォローアップ質問です。 バックグラウンド MSDNデリゲートチュートリアル(C#)から作業すると、次のようになります。 デリゲートが作成されると、関連付けられているメソッドは変更されないことに注意してください。デリゲートオブジェクトは不変です。 そして、コードサンプルでこれを確認します(コード全体を少し広げます)。 public delegate void ProcessBookDelegate(Book book); bookDB.ProcessPaperbackBooks(new ProcessBookDelegate(PrintTitle)); bookDB.ProcessPaperbackBooks(new ProcessBookDelegate(totaller.AddBookToTotal)); 質問 ここで明らかに、ここでのコードの記述方法により、プロセスごとに新しいデリゲートが作成されます。私は推測あなたのようなものを行うためにしようと不変性が関連しています ProcessBookDelegate thisIsATest = new ProcessBookDelegate(PrintTitle); ProcessBookDelegate thisIsATest = new ProcessBookDelegate(totaller.AddBookToTotal); thisIsATest不変であるときにどれをコンパイルする必要がありますか?では、Microsoftを不変にすることでどのような問題を解決したのでしょうか。C#6がデリゲートを変更可能にした場合、どのような問題が発生しますか? 編集 私は不変性がこれを防ぐと信じています: ProcessBookDelegate thisIsATest = new ProcessBookDelegate(PrintTitle); thisIsATest.ChangeTheDelegateInABadFashion(); someFunction(thisIsATest); //This function works as normal //because the delegate is unchanged //due to immutability しかし、不変性はこれを防止しません: …

5
文字列は不変ですが、なぜすべてが定数ではないのですか?
stringタイプは不変です。 .NETのような高級言語でconstキーワードを使用できstringsます。'const'についての私の理解は一定を意味します(同じままで、値を変更することはできません)。 strings常にではありませんかconstant(IMOの用語constantは、値のライフタイムを意味するたびに型を再作成する必要がある場合、同じコンテキストでは適用できません)、それは一定でした)? 高水準言語、特に.NET(私もJavaに興味があります)では、これはオブジェクトの一般的なメモリ管理/追跡によるものですか、それとも別の理由がありますか?
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.