2013-04-23 72 views
1

當在「foreach」循環中刪除時,在Azure表中刪除實體時,我還沒有一致的結果。 PartitionKey是唯一的。在ForEach循環中刪除Azure表實體的最佳做法

是否有最佳做法,人們可以推薦?

爲了簡潔,我省略了Try..Catch語句。

假設:

var context = new FooContext(_storageAccount); 

     var query = (from e in context.TableBar 
           where e.RowKey == rowKey 
           select e).AsTableServiceQuery(); 

方法#1

   foreach (var entity in query.Execute()) 
      { 
        // delete each entity 
        context.DeleteObject(entity); 
        context.SaveChanges(); 
      } 

方法#2

  foreach (var entity in query.Execute()) 
      { 
        // delete each entity 
        context.DeleteObject(entity); 
      } 
      context.SaveChanges(); 

方法#3

  var bars = query.Execute(); 
      foreach (var bar in bars) 
       context.DeleteObject(bar); 
      context.SaveChanges(); 

方法#1似乎刪除了大多數實體,但通常最後的實體不會刪除。這是一個有效的實體。

+1

那麼,你想要刪除具有相同RowKey但不同的PartitionKey的實體嗎?這有點奇怪,可能是緩慢和不完全刪除的原因。 Azure存儲無法高效地掃描所有的PartitionKey,因此您應該考慮熟知或修復PartitionKey,而不是RowKey。 http://www.windowsazure.com/en-us/develop/net/how-to-guides/table-services/#concepts – Pascal 2013-04-23 15:07:01

+0

謝謝你們的迴應。在做了更多的研究後,我找到了解決我的問題的決議。請參閱以下[StackOverflow問題](http://stackoverflow.com/questions/7590383/error-deleting-from-azure-cloud-table-resourcenotfound)。 – user1219694 2013-04-24 04:28:52

回答

24

如果您已經知道實體的PartitionKey和RowKey,則不必首先加載它。最快的方法是直接使用CloudTable和DynamicTableEntity這樣的:

var cloudTable = cloudTableClient.GetTableReference("TheTable"); 

var entity = new DynamicTableEntity("ThePartitionKey", "TheRowKey"); 
entity.ETag = "*"; 

cloudTable.Execute(TableOperation.Delete(entity)); 

如果你想刪除你不知道RowKeys那麼實體的集合,你需要先和使用加載實體一個Batch Operation刪除實體。此外,您不需要加載實體的所有屬性,我們只需要知道RowKey,以便我們可以再次使用與上述相同的技術。爲此,我們要小心的Projection Query

var batchOperation = new TableBatchOperation(); 

// We need to pass at least one property to project or else 
// all properties will be fetch in the operation 
var projectionQuery = new TableQuery<DynamicTableEntity>() 
    .Where(TableQuery.GenerateFilterCondition("PartitionKey", 
     QueryComparisons.Equal, "ThePartitionKey")) 
    .Select(new string[] { "RowKey" }); 

foreach (var e in table.ExecuteQuery(projectionQuery)) 
    batchOperation.Delete(e); 

table.ExecuteBatch(batchOperation); 

一句話:一個批量操作允許在必須共享相同的PartitionKey,所以你可能需要將實體分割成適當的批次批次最多100個實體爲此工作。