
はじめまして。
この度、Javaサーブレットを利用したWEBアプリケーションを開発しようとしています。
オブジェクト指向言語での開発は初めてのため、クラス図に表れるエンティティの扱いに困っています。
例えば、アマゾンのような大規模なサイトの場合、「会員」エンティティ、「書籍」エンティティ、顧客を分類する「地域」エンティティ等は、まともにインスタンス化すれば100万以上存在すると思われますが、これらはすべてインスタンス化されメモリに常駐するものなのでしょうか?
その場合はどの程度のサーバスペックと台数が必要でしょうか?
それとも設計は無視して一ユーザがアクセスする度にセッション内にデータベースから1レコード分のインスタンスを生成し、検索はインスタンスではなくSQLですませてしまうものなのでしょうか?
設計から実装する場合において、そのエンティティのデータが大量になる場合はどのようなテクニックがありますか?
ご教授宜しくお願いします。
No.3ベストアンサー
- 回答日時:
#2です。
> 例えば、ある会員が予約している書籍を一覧表示する場合、
> オブジェクト指向的に考えれば、
> 会員クラスが保持する予約リストフィールドに書籍クラスのインスタンスを保持するような設計になると考えております。
(「クラス」と「インスタンス」の使い分けが少し気になりますが)オブジェクト指向的にデータ構造を設計するとsnake103さんの書かれたとおりになると思います。
> でもこの場合、
> 結局書籍インスタンスがすべて必要になり、
> 100万件分のインスタンスのメモリ領域が必要になると考えております。
> 逆にSQLでやる場合は、
> 一覧表示をする際にその都度、
> SQLを発行しリストを生成する感じになると考えます。
> この方法はクラス図の設計を無視していると思うのですが、
> 私の考えが間違っていますでしょうか?
この部分が少し違っていて、基本的にオブジェクト指向データ設計と、メモリ/ディスク(データベース)の別は切り離して考えるべきではないかと思います。
もっと正確にいうと、ビジネスロジック層のデータ構造(抽象データ構造=オブジェクト指向データ構造)と、ストレージ層以下で使われるデータ構造(物理データ構造=メモリ/データベース(ディスク))は、分けて考えるものではないかということです。
書籍の例を用いて、少し具体的に説明してみます。
会員クラスが以下のように定義されているとします。
(擬似Javaコード)
class Kaiin
{
int kaiinId;
ShosekiList yoyakuList;
//コンストラクター
Kaiin(int Id) {
this.kaiinId = Id;
}
ShosekiList getYoyakuList() {
if (yoyakuList == null) { //[※]
getYoyakuListFromStorage();
}
return this.yoyakuList;
}
private ShosekiList getYoyakuListFromStorage() {
// データベースからthis.kaiinIdの予約リストを検索して
// KaiinインスタンスのyoyakuListに格納する処理
this.yoyakuList = ...;
return this.yoyakuList;
}
}
ここでは、予約リストを取り出す際、[※]で、もし予約リストがすでにメモリ上にあればそれを使い、なければデータベースから取ってくるようになっています。
上のクラスを利用すると、ある会員の予約リストを取り出す処理は、
Kaiin k = new Kaiin(id);
ShosekiList sl = k.getYoyakuList();
となり、予約リストがメモリ上にあるかデータベースから取ってくるかを意識する必要はありません。
ちなみに、どのようなインスタンスに対しても[※]のような処理を自動的にやってくれるのが、#2で挙げたJ2EE/EJBなどのフレイムワークと考えてください。
大変わかりやすいご回答有難うございました。
納得です。
これを機にJ2EEパターン等より勉強していきたいと思います。
また機会がありましたら宜しくお願いします。
No.2
- 回答日時:
> それとも設計は無視して一ユーザがアクセスする度にセッション内にデータベースから1レコード分のインスタンスを生成し、検索はインスタンスではなくSQLですませてしまうものなのでしょうか?
「設計は無視して」のところが気になりますが、こちらが正解だと思います。
ある程度大規模なWebアプリの設計には、現在では通常「三層モデル」(3 tier model)が用いられます。これは、アプリを「フロントエンド」「ビジネスロジック」「ストレージ」(必ずしもこの呼称が使われているとは限りませんが)に分けて考える手法です。
「会員」「書籍」「地域」などのエンティティの扱いは、ビジネスロジック層に相当します。この層では、それをメモリにロードするかデータベースに格納するかなどということは意識せず、インスタンスとして扱い、ロジックを組み立てます。
メモリへのロードやデータベースへの格納は、ストレージ層で隠蔽します。こうした隠蔽に用いられるテクニックとして、J2EEコンテナーやEJBなどがあります。
以上、非常に大ざっぱな説明ですが…。
もっと詳しい情報は、ここに出てきた単語を検索すれば得られると思います。
この回答への補足
早速のご回答ありがとうございます。
補足で以下の考え方が正しいか教えていただけませんか?
例えば、ある会員が予約している書籍を一覧表示する場合、オブジェクト指向的に考えれば、会員クラスが保持する予約リストフィールドに書籍クラスのインスタンスを保持するような設計になると考えております。でもこの場合、結局書籍インスタンスがすべて必要になり、100万件分のインスタンスのメモリ領域が必要になると考えております。逆にSQLでやる場合は、一覧表示をする際にその都度、SQLを発行しリストを生成する感じになると考えます。この方法はクラス図の設計を無視していると思うのですが、私の考えが間違っていますでしょうか?
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
変数名の付け方
-
オブジェクト参照がオブジェク...
-
「インスタンス」の意味をわか...
-
インスタンス参照でアクセスで...
-
複数の変数を宣言する時、同時...
-
VB.NET getとsetの概念がわかり...
-
クラス型がインスタンス化され...
-
private static という変数の修飾
-
フォームの存在をチェックする方法
-
データベースから日付型を取得...
-
C# インスタンスの破棄
-
文字列を日付に変換でParseExce...
-
Eclipse3でVisualEditorが起動...
-
VB.netで標準モジュールからフ...
-
C#のメモリ解放についてご教授...
-
生成したインスタンスを削除す...
-
インスタンスを同じ名前で作成...
-
インスタンスフィールドの初期...
-
《instantiate》(インスタンス...
-
newしないインスタンス?実体化...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
private static という変数の修飾
-
変数名の付け方
-
複数の変数を宣言する時、同時...
-
インスタンス参照でアクセスで...
-
生成したインスタンスを削除す...
-
オブジェクト参照がオブジェク...
-
C#において、同じインスタンス...
-
C# インスタンスの破棄
-
変数の参照でエラーが出てしま...
-
インスタンスを同じ名前で作成...
-
VB.NET getとsetの概念がわかり...
-
newしないインスタンス?実体化...
-
javaのクラスの作り方、エラー...
-
非staticフィールドを参照でき...
-
「インスタンス」の意味をわか...
-
[Visual C#] 優先される処理に...
-
フォームの存在をチェックする方法
-
大量のデータとインスタンスの...
-
C#「オブジェクト参照が必要で...
-
String a = "a"; と String b =...
おすすめ情報