序章
私は GAE を初めて使用し、データストアにあまりデータがないにもかかわらず、残念ながら 1 日あたりのデータストア読み取りのクォータ制限に非常に急速に達する小さなアプリを作成しました。
この質問は、レイアウトとインデックスの可能な使用に関するものでなければなりません (現在、それらの使用方法についての手がかりがありません)。
アプリがすべきこと
- アプリは、カードゲームでスコアを追跡する必要があります (興味のある方はTichu ^^)。ゲームはいくつかのラウンドで構成され、1 つのチームが 1000 ポイントに達するとすぐに終了します。
- アプリは、プレイしたゲームの統計情報を表示する必要があります
アプリの最初のレイアウト
私の最初のレイアウト アプローチは、次のエンティティを使用していました。
class Player(db.Model):
Name = db.StringProperty(required = True)
class Game(db.Model):
Players = db.ListProperty(db.Key)
Start = db.DateTimeProperty(auto_now_add = True, required = True)
End = db.DateTimeProperty()
class Round(db.Model):
Game = db.Reference(Game, required = True)
RoundNumber = db.IntegerProperty(required = True)
PointsTeamA = db.IntegerProperty(required = True)
PointsTeamB = db.IntegerProperty(required = True)
FinishedFirst = db.ReferenceProperty(Player, required = True)
TichuCalls = db.ListProperty(db.Key)
上記でわかるように、エンティティは正規化されています (少なくとも正規化されていることを願っています)。ただし、このアプローチでは、次のような単純な計算が行われます
- 最も多くの試合に勝った選手は?
これは次のようになります
#Untested snippet just to get an idea of what I am doing here
Wins = dict.fromkeys(Player.all().fetch(None), 0)
for r in Round.all():
wins[r.FinishedFirst] += 1
しかし、次のような他の統計も
- 最も頻繁に最初に終了したプレーヤー
- 勝率が最も高い選手は?
- 等
非常に大量のデータセット読み取り操作が発生します。限られた量の統計情報のみを表示するページでは、わずか 60 ラウンドで 1 ハンドがゲームでいっぱいで、数回の更新で 1 日の割り当てに達しました。また、memcache を使用しても問題は解決しませんでした。
これが私の2番目のアプローチにつながりました:
アプリの 2 番目のレイアウト
class Player(db.Model):
Name = db.StringProperty(required = True)
class Game(db.Model):
Players = db.ListProperty(db.Key)
Start = db.DateTimeProperty(auto_now_add = True, required = True)
End = db.DateTimeProperty()
Rounds = db.BlobProperty()
def GetRounds(self):
if self.Rounds:
return pickle.loads(self.Rounds)
else:
return []
def AddRound(self, R):
Rounds = self.GetRounds()
Rounds.append(R)
self.Rounds = pickle.dumps(Rounds, -1)
class Round(object):
def __init__(self, Game, RoundNumber, PointsTeamA, PointsTeamB, FinishedFirst, TichuCalls):
self.Game = Game
self.RoundNumber = RoundNumber
self.PointsTeamA = PointsTeamA
self.PointsTeamB = PointsTeamB
self.FinishedFirst = FinishedFirst
self.TichuCalls = TichuCalls
現在、everyGame
は、もはや ではなくなったラウンドのリストを格納していdb.Model
ます。これにより、データセットの読み取り量が大幅に削減されます。
質問
- データモデルをどのように設定しますか?
BlobProperty
(型ではない格納オブジェクトを使用するのは理にかなっていますdb.Model
か?) - このモデルのインデックスはどのようになりますか? (インデックスについての理解が非常に限られているため、詳しく説明してください。)
- データストア内の要素の数が増えると、1 日あたりの読み取りのクォータは、最終的には 2 番目のアプローチでも到達します。モデルを設計する際に、この事実をどのように考慮しますか?