2011-08-11 4 views
6

다차원 관계를 가진 두 개의 모델 인 Transaction과 Person이 있습니다. 각 거래에는 인원이 포함되어 있습니다. 각 개인의 경우, 해당 개인이 연결된 각 거래에 연결된 금액도 있습니다. 따라서 관계 데이터를 사용하여 다 대다 관계를 모델링해야합니다. 나는이 같은 모델이이 방법으로Google App Engine에서 관계 데이터를 사용하여 다 대다 모델링하기

http://code.google.com/intl/sv-SE/appengine/articles/modeling.html

:

class TransactionPerson(db.Model): 
    # References 
    transaction = db.ReferenceProperty(Transaction, required=True) 
    person = db.ReferenceProperty(Person, required=True) 
    # Values 
    amount = db.FloatProperty(required=True) 

을하지만 사람마다 양을 요약해야하는 경우 때문에 나는 성능이 아주 나쁜 찾을 구글은이 방법을 제안한다 모든 트랜잭션에서 금액을 합산하면서 "조인"을 구현하기 위해 Person * Transaction * TransactionPerson 시간을 반복해야합니다.

내 생각

내 생각은 트랜잭션 모델이리스트하는 것입니다 :

class Transaction(db.Model): 
    persons = ListProperty(db.Key) 
    persons_amount = ListProperty(float) 

내가 관련 찾기 위해 각각의 사람에 대한 모든 TransactionPerson을 통해 루프를하지 않아도이 방법을 트랜잭션. 그리고 여전히 사람을 기반으로 트랜잭션을 쿼리 할 수 ​​있습니다.

질문

  1. 이 가능합니까? 저장/검색 할 때 목록 순서가 항상 동일하므로 목록간에 색인이 동기화됩니다.
  2. 관련 데이터와 다 대 다 관계를 구현하는 좋은 방법입니까?

답변

2

나는 당신이 틀린 문제를 해결하고 있다고 생각합니다. 중간 관계 엔티티는 좋은 접근 방식입니다. 문제는 요약을 계산하는 데 시간이 오래 걸린다는 것입니다. 당신은 그것에 대해 더 염려해야합니다.

먼저의 요약 데이터를 으로 계산하는 것이 가장 좋습니다.

"1 인당 거래 합계"의 특정 경우에는 사용자 모델에 추가 필드를 추가하고 모든 트랜잭션의 누적 합계로 업데이트하려는 것입니다. 요약 값이 항상 올바르도록 TransactionPerson이 수정 될 때마다이 값을 업데이트해야합니다.

+0

그러나 왜 덜 효율적인 작업을 야기 할 때 중급 연관 엔터티가 좋은 접근 방법입니까? 예를 들어 당신의 접근법; 트랜잭션이 업데이트되면 트랜잭션과 관련된 모든 Person 객체를 자주 업데이트해야합니다. 내 접근 방식을 사용하면 필요하지 않습니다. 협회 법인을 사용하는 것이 더 나은 이유는 무엇입니까? – thejaz

+0

둘 중 어느 것이 더 나은 선택 일지 모르겠지만, 제 대답은 요약 데이터를 계산하는 특정 질문에 초점을 맞추고 있습니다. 특정 요청을 만족시키기 위해 소수 이상의 엔티티를로드해야하는 경우 값이 변경 될 때와 같이 요청에서 해당 프로세스를 추출하고 다른 방식으로 빌드하는 방법을 찾아야 할 것입니다. – SingleNegationElimination

+0

요약 데이터는 한 가지 예일뿐입니다. 나는 종종 거래에서 모든 사람을 얻고 싶다. 나는 실제적으로 동일한 Person * Transaction * TransactionPerson 루프를 가지기를 원한다. 비록 그것이 더 희귀 할지라도 (나는 TransactionPerson을 추가하거나 편집 할 때조차도), 현명한 성능으로 받아 들일 수 없다. 거래에 해당 데이터 (사람 목록)를 캐싱해야한다고해도 내 질문에서 제안한 것과 동일하지만 목록에 관계 데이터가 추가되어 있습니다. 중복 된 데이터로 이어지지는 않습니다. 어떻게 할 건데? – thejaz

1

예. 유지 관리중인 주문에 의존 할 수 있습니다. docs :

엔터티가 쿼리 및 get()에 의해 반환 될 때 목록 속성 값은 저장된 순서와 같습니다. 한 가지 예외가 있습니다. Blob 및 Text 값이 목록의 끝으로 이동합니다. 그러나, 그들은 원래 순서를 서로 유지합니다.

2. 예, ListProperties는 비정규 관계를 제거하는 친구입니다. 나는 데이터를 많이 복제하는 경향이 있으며, 이렇게 정규화되지 않은 데이터의 '캐시'와 같은 목록 속성을 사용합니다.

+0

(2)에 대해서는 데이터 복제와 관련하여 어떤 의미입니까? 필자의 경우 중복이 아니며 단지 실제 데이터를 저장하는 유일한 방법 일뿐입니다. – thejaz

+0

때로는 정규화 된 설정을 유지하기 위해 'A는 B가 많습니다.'하지만 'B'를 저장할 때마다 빠른 데이터 처리를 위해 'A'의 목록에 중요한 데이터 중 일부를 캐시합니다. –