[解決済み] オブジェクトの配列としての状態 vs. idをキーとしたオブジェクトの状態
疑問点
の章では ステートシェイプの設計 の章では、IDをキーとするオブジェクトに状態を保持することが提案されています。
IDをキーとして保存されたオブジェクトにすべてのエンティティを保持し、他のエンティティやリストからそれを参照するためにIDを使用します。
彼らは続けて次のように述べています。
<ブロッククオートアプリの状態をデータベースと考えましょう。
私はフィルターのリストの状態形状に取り組んでおり、そのうちのいくつかは開いている (ポップアップで表示される)、または選択されたオプションを持っています。アプリの状態をデータベースとして考える」を読んで、API (それ自体がデータベースによってバックアップされる) から返される JSON 応答としてそれらを考えることについて考えました。
というように考えていました。
[{
id: '1',
name: 'View',
open: false,
options: ['10', '11', '12', '13'],
selectedOption: ['10'],
parent: null,
},
{
id: '10',
name: 'Time & Fees',
open: false,
options: ['20', '21', '22', '23', '24'],
selectedOption: null,
parent: '1',
}]
しかし、ドキュメントによると
{
1: {
name: 'View',
open: false,
options: ['10', '11', '12', '13'],
selectedOption: ['10'],
parent: null,
},
10: {
name: 'Time & Fees',
open: false,
options: ['20', '21', '22', '23', '24'],
selectedOption: null,
parent: '1',
}
}
理論上は のデータがシリアライズ可能である限り、問題にはならないはずです(見出し "State"の下)。 .
というわけで、Reducerを書くまでは、喜んでarray-of-objectsのアプローチで行っていました。
オブジェクト・キー・バイ・IDのアプローチ(およびスプレッド構文の自由な使用)で
OPEN_FILTER
の部分は
switch (action.type) {
case OPEN_FILTER: {
return { ...state, { ...state[action.id], open: true } }
}
一方、array-of-objectsのアプローチでは、より冗長な(そしてヘルパー関数に依存する)ものである。
switch (action.type) {
case OPEN_FILTER: {
// relies on getFilterById helper function
const filter = getFilterById(state, action.id);
const index = state.indexOf(filter);
return state
.slice(0, index)
.concat([{ ...filter, open: true }])
.concat(state.slice(index + 1));
}
...
そこで、質問は3つあります。
1) Reducer のシンプルさは、object-keyed-by-id アプローチを採用する動機となりますか?その状態の形状に他の利点がありますか?
そして
2) Object-keyed-by-id のアプローチでは、API のための標準的な JSON in/out を扱うのが難しくなるように思えます。(その場合、JSON形式とstate shape形式を行き来するための関数を使うだけなのでしょうか?(そのアプローチを提唱する場合、その理由の一部は、上記のオブジェクトの配列のリデューサよりも不格好ではないということでしょうか?)
そして
3) Dan Abramov が redux を理論的には状態-データ-構造にとらわれないように設計したことは知っています (これは "慣習上、トップレベルの状態はオブジェクトやMapのようなキーバリューのコレクションですが 技術的には任意の型にすることができます。 ," を強調しています)。それとも、オブジェクトの配列を使用することによって、その計画を中止して、IDによってキーが設定されたオブジェクトに固執しようとするような、予期しないペインポイントがあるのでしょうか?
どのように解決するのですか?
Q1: リデューサがシンプルなのは、配列の中から正しいエントリを探す必要がないためです。配列の中を探さなくてよいというのは利点です。セレクタや他のデータアクセサは、これらの項目に対して
id
. アクセスのたびに配列内を検索しなければならないのは、性能上の問題となります。配列が大きくなると、パフォーマンスの問題は急激に悪化します。また、アプリケーションがより複雑になり、より多くの場所でデータを表示したりフィルタリングしたりするようになると、この問題も悪化します。この組み合わせは不利になりかねません。アイテムにアクセスする際に
id
でアクセスすると、アクセス時間が
O(n)
から
O(1)
であり、大きな
n
(ここでは配列項目)では大きな違いになります。
Q2:このような場合は
normalizr
を使うと、APIからストアへの変換を助けることができます。normalizr V3.1.0の時点では、他の方法に行くためにdenormalizeを使用することができます。とはいえ、アプリはデータの生産者よりも消費者が多く、そのためストアへの変換は通常より頻繁に行われます。
Q3: 配列を使用することで発生する問題は、ストレージの規約や非互換性の問題ではなく、パフォーマンスの問題だと思うのですが。
関連
-
[解決済み] 配列から特定の項目を削除するにはどうすればよいですか?
-
[解決済み] JavaScriptでオブジェクトをディープクローンする最も効率的な方法は何ですか?
-
[解決済み] JavaScript で配列に値が含まれているかどうかを確認するにはどうすればよいですか?
-
[解決済み] JavaScriptのオブジェクトが空であることをテストするにはどうすればよいですか?
-
[解決済み] オブジェクトが配列であるかどうかを確認するにはどうすればよいですか?[重複]。
-
[解決済み] HTML5のlocalStorageにオブジェクトを格納する方法は?
-
[解決済み] JavaScriptのオブジェクトの配列からidでオブジェクトを検索する
-
[解決済み】オブジェクトの配列を文字列のプロパティ値でソートする
-
[解決済み】オブジェクトからプロパティを削除する(JavaScript)
-
[解決済み] $.ajax実行中にローディングイメージを表示する
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] javascript の関数から `undefined` と `null` のどちらを返すのが良いのでしょうか?
-
[解決済み] 兄弟ノードを選択する方法はありますか?
-
[解決済み] JavaScriptのtoString()関数をオーバーライドして、デバッグ用に意味のある出力を提供することは可能でしょうか?
-
[解決済み] 無効になっている入力フィールドの値を送信する
-
[解決済み] JavaScriptで文字列を数値に変換する最速の方法は何ですか?
-
[解決済み] Javascriptで動的に命名されたメソッドを呼び出すにはどうすればよいですか?
-
[解決済み] jqueryはjavascriptのライブラリなのかフレームワークなのか?[クローズド]
-
[解決済み] CORS: 認証モードは 'include' です。
-
[解決済み] Prototypeを使ってtextareaを自動サイズ調整するには?
-
[解決済み] JavaScript で `throw` の後に `return` をする必要がありますか?