2015-05-04 132 views
0

假設我有一個關於Parse的表格,它有兩列:手動設置的標識符和數字屬性。如何獲得唯一鍵列表的列的最大值列表

我需要編寫一個查詢,獲取每個唯一標識符的numeric屬性的最大數目。因此,在下面的例子:

| identifier | value | 
---------------------- 
| 1   | 10 | 
| 2   | 5  | 
| 1   | 7  | 
| 2   | 9  | 

我希望下面的輸出:

| identifier | value | 
---------------------- 
| 1   | 10 | 
| 2   | 9  | 

現在我知道解析沒有像集團的任何東西報表,所以這可能是不可行的單查詢。

在這種情況下,您會提出什麼建議?我看到一些解決方案,每個都有嚴重的缺點:

  • 撰寫來自多個查詢的結果。這將需要一個查詢獲取唯一的標識符列表,然後爲每個標識符分別查詢以獲得最大值。如果表格增長的話,這可能不會很好地擴展。此外,結果並不完全一致,因爲數據庫可以在查詢之間進行更改(對於我的用例,稍微過時的日期並不算太糟糕)。這將嚴重影響請求配額限制,因爲單個請求現在可以觸發大量請求。
  • 保留一個單獨的表,以跟蹤此結果。該表格對每個標識符都有一行,包含最大值。爲此,我需要一個更新第二個表的beforeSave觸發器。從我讀過的內容來看,並不保證beforeSave觸發器不會同時執行,所以確保我不會爲相同標識符意外插入多個值非常棘手。我可能不得不運行後臺作業,刪除重複。

對於我的用例,我需要在iOS設備上獲取數據,因此網絡流量也是一個問題。

+0

您打算處理多少個唯一ID?你的桌子有多大?我可以考慮使用2-3種方法來處理複合查詢或子查詢的這個問題,但知道您的集合大小將有助於優化,因爲Parse限制返回到最大1000個項目。 –

+0

會有大約30-100個唯一的ID。我希望每個唯一ID至多有幾百個條目。 –

回答

0

鑑於這些限制,我認爲您最好的選擇是使用CloudCode afterSave事件。 beforeSave可能會導致用戶體驗過度放緩。

您可以通過在更改最大值表之前查詢最大值表並刪除該標識符存在的任何值來解決併發觸發器問題。事情是這樣的:

Parse.Cloud.afterSave("Yourclass", function(request) { 
    var objectToSave = request.object; 
    query = new Parse.Query("Maxvaluetableclass"); 
    query.equalTo("identifier", objectToSave.identifier); 
    query.lessThan("value", objectToSave.value); 
    query.find({ 
    success: function(results) { 
     //Delete all the objects in the max value table with smaller values 
     for (var i = 0; i < results.length; i++) { 
     var object = results[i]; 
     object.destroy(); 
     } 
     var Maxvaluetableclass = Parse.Object.extend("Maxvaluetableclass"); 
     var maxValueObject = new Maxvaluetableclass(); 
     maxValueObject.identifier = objectToSave.identifier; 
     maxValueObject.value = objectToSave.value; 
     maxValueObject.save(); 
    }, 
    error: function(error) { 
     //All current values are larger, so do nothing 
    } 
    }); 
}); 

UPDATE:你會發現,這種改進的設置是「自潔」 - 每次運行時,它會刪除所有的小件物品。這意味着你不必運行後臺功能

+0

這解決了Maxvaluetableclass中重複的問題,但我看不到它如何確保保存正確的最大值。如果afterSave由兩個較大值的插入觸發,並且第二個觸發器在第一個觸發器完成刪除之前完成查詢,則保存的最大值僅爲寫入的最後一個值。 –

+0

好點。我已經更新了我的答案,讓系統'自我清理' - 'afterSave'函數的每次運行都會刪除最大值表中的較小值,並且兩個併發保存現在應該相互配合。 –

0

@Ryan Kreager:我沒有50reps,所以我無法評論以前的答案。 參考你的回答,OP應該考慮觸發這種後果的頻率。因爲如果你有很多記錄,那麼for循環中的每個destroy()都會計爲1個API請求。如果我在Parse中正確理解定價。

https://www.parse.com/plans/faq