2010-04-07 33 views
5

我的問題的根源在於C#編譯器太聰明瞭。它檢測到一個對象可能未定義的路徑,因此要求我填充它。在代碼中,我查看DataSet中的表以查看是否有我想要的表。如果不是,我創建一個新的。我知道dtOut總是會被分配一個值,但是編譯器不會很高興,除非它在聲明時被分配了一個值。這是不雅的。如何避免以優雅的方式創建不需要的對象?

如何以更優雅的方式重寫此文件?

   System.Data.DataTable dtOut = new System.Data.DataTable(); 
      . 
      . 
      // find table with tablename = grp 
      // if none, create new table 
      bool bTableFound = false; 
      foreach (System.Data.DataTable d1 in dsOut.Tables) 
      { 
       string d1_name = d1.TableName; 
       if (d1_name.Equals(grp)) 
       { 
        dtOut = d1; 
        bTableFound = true; 
        break; 
       } 
      } 

      if (!bTableFound) dtOut = RptTable(grp); 
+0

謝謝大家的意見。 (我對一般問題感興趣,給出的代碼只是一個例子,但沒有特別的重要性。) – SeaDrive 2010-04-08 14:54:04

回答

11

初始值可以是null。編譯器不需要你創建實例;它只是要求你分配一個值。

System.Data.DataTable dtOut = null; // compiler is now happy 
// rest of code as before 
+0

我認爲這是最簡單和最優雅的方式,我會做。 – Robo 2010-04-07 22:45:01

+0

這可能是我編程複雜程度的最佳答案,但對我來說似乎仍然不夠雅緻。挑剔,挑剔。 – SeaDrive 2010-04-08 14:39:46

11

你可以重寫你的方法,像這樣:

System.Data.DataTable dtOut = dsOut 
            .Tables 
            .Cast<System.Data.DataTable>() 
            .FirstOrDefault(t => t.TableName.Equals(grp)) 
           ?? RptTable(grp); 
+0

這使用了我不熟悉的功能:一個學習機會。 – SeaDrive 2010-04-08 14:32:53

+0

@SeaDrive:這是基於LINQ(用於cast + FirstOrDefault)和空合併運算符(??)來處理空檢查。它取代了你的整個方法。 – 2010-04-08 15:55:54

0
var dtOut = dsOut != null && dsOut.Tables != null && dsOut.Tables[grp] != null 
      ? dsOut.Tables[grp] 
      : RptTable(grp); 

HTH

+1

爲什麼-1沒有任何評論?也許SO應該對反對票強制執行評論,以便我們可以瞭解到底出了什麼問題...... – Sunny 2010-04-07 21:44:21

+0

Fair point,Sunny。我的猜測是這個問題是針對C#的,但你的答案不是。 – Tim 2010-04-07 21:48:32

+0

爲什麼我的代碼不是c#? – Sunny 2010-04-08 00:17:49

1
  ...program... 
      { 
       System.Data.DataTable dtOut = GetDataTableByName(grp, dsOut); 
      } 

      public DataTable GetDataTableByName(string grp, object dsOut) 
      { 
       foreach (System.Data.DataTable d1 in dsOut.Tables) 
       {      
        if (d1.TableName.Equals(grp)) 
        return RptTable(grp) 
       } 
       return null; 
      } 

如果我interperated你正確命名。

0

我喜歡Otávio的回答,不過這裏有一個替代方法。你可以倒推foreach循環到它自己的方法,這樣的:

static System.Data.DataTable 
getDataTable (System.Data.DataTable[] tables, String grp) 
{ 
    foreach (System.Data.DataTable d1 in tables) 
     { 
      string d1_name = d1.TableName; 
      if (d1_name.Equals(grp)) 
      { 
       return d1; 
      } 
     } 
    return null; 
} 

這使您可以簡化您的原始方法:

System.Data.DataTable dtOut = getDataTable(dsOut.Tables, grp); 
if (!dtOut) dtOut = RptTable(grp); 
0

如果你想優雅,去LINQ:

var dtOut = 
    dsOut.Tables.FirstOrDefault(t => t.TableName == grp) 
    ?? RptTable(grp); 
相關問題