2010-06-01 60 views
0

我被一個關於泛型類的問題困住了。我很困惑如何使用參數調用構造函數。泛型類VB.NET

我的界面:

Public Interface IDBObject 
    Sub [Get](ByRef DataRow As DataRow) 
    Property UIN() As Integer 
End Interface 

我的子類:

Public Class User 
    Implements IDBObject 

    Public Sub [Get](ByRef DataRow As System.Data.DataRow) Implements IDBObject.Get 

    End Sub 

    Public Property UIN() As Integer Implements IDBObject.UIN 
     Get 

     End Get 
     Set(ByVal value As Integer) 

     End Set 
    End Property 
End Class 

我的下一個類:

Public Class Users 
    Inherits DBLayer(Of User) 

#Region " Standard Methods " 

#End Region 
End Class 

我DBOBJECT類:

Public Class DBLayer(Of DBObject As {New, IDBObject}) 

    Public Shared Function GetData() As List(Of DBObject) 
     Dim QueryString As String = "SELECT * ***;" 
     Dim Dataset As DataSet = New DataSet() 
     Dim DataList As List(Of DBObject) = New List(Of DBObject) 

     Try 
      Dataset = Query(QueryString) 
      For Each DataRow As DataRow In Dataset.Tables(0).Rows 
       **DataList.Add(New DBObject(DataRow))** 
      Next 
     Catch ex As Exception 
      DataList = Nothing 
     End Try 
     Return DataList 
    End Function 
End Class 

我在DBLayer對象的加星區域出現錯誤。

可能的原因是什麼?我能做些什麼來解決它?

我甚至想在IDBObject接口中添加New(byval someval as datatype)作爲重載構造。但它也給出了一個錯誤?我該怎麼做?

加入

的Sub New(BYVAL的DataRow如DataRow中)在IDBObject producess以下錯誤 '的Sub New' 不能在接口中聲明。

錯誤DBLayer對象 線製作人:DataList.Add(新澤西DBOBJECT(DataRow中)) 消息:參數不能被傳遞到上一個類型參數「新建」使用。

+0

你會得到什麼錯誤? – 2010-06-01 12:01:09

回答

0

它不是很簡單,因爲它對你指的是什麼感到困惑?你已經將「DataRow作爲DataRow作爲DataRow」這一行看起來像是混淆的祕訣,它可能是當你在構造函數中引用DataRow時,它不是使用循環變量,而是使用數據類型「DataRow」。即使這不是問題,您可能想要將您的循環變量更改爲不太模糊的東西。

你得到的實際錯誤是什麼?

同樣對於添加額外構造函數的最後部分,你會得到什麼錯誤?如果你正在向接口添加一些符號,你是否將額外的構造函數添加到了實現該接口的每個符號上?

+0

它不是循環錯誤...我添加了正在生成的錯誤 – KoolKabin 2010-06-01 12:00:56

0

爲構造函數,這是因爲你不能在接口中定義構造函數。

編輯:

我明白你現在要做的。你想創建一個DBLayer定義的通用類型的新實例。你的問題將是你不能指定你的接口的實現需要一個特定的構造函數。你可能更適合在接口上接受DataRow的方法,並使用它來初始化IDBObject,然後可以創建DBObject類型的實例,然後調用接受DataRow的方法來初始化實例。

或者你可以要求你的DBLayer類需要能夠產生類型DBOBJECT的對象給出一個DataRow一個工廠類,你可以調用工廠的這種方法來代替調用

 For Each rowAs DataRow In Dataset.Tables(0).Rows 
      //DataList.Add(New DBObject(row)) 
      DataList.Add(m_factory.CreateObject(row)); 
     Next 

EDIT 2:

最簡單的方法將是擴大你的界面允許您設置的DataRow並調用在循環的方法:

 For Each row As DataRow In Dataset.Tables(0).Rows 
      //DataList.Add(New DBObject(row)) 
      Dim newElement As IDBObject = CType(Activator.CreateInstance(GetType(DBObject)), IDBObject) 
      //you'll need to add this SetDataRow method the the IDBObject interface 
      newElement.SetDataRow(row) 
      DataList.Add(newElement) 
     Next 
+0

所以我可以做什麼如果我想要做DataList.Add(新DBObject(DataRow)) 選擇不同的名稱也不是解決這個問題 – KoolKabin 2010-06-01 12:05:28

+0

混淆m)工廠或類工廠...我不是太高級別的程序員...需要一些更基本的概念...你可以plz詳細說明 – KoolKabin 2010-06-01 12:44:31

+0

編輯我的答案詳述 – 2010-06-02 08:41:49

1

問題是新的約束。它只承諾一個無參數的構造函數,編譯器不能推斷DbObject類型參數可能有一個將DataRow作爲參數的構造函數。

您或許可以通過獲取/設置DataRow的屬性來擴展IDbObject接口。一個班級工廠會很有幫助。

0

如果使用抽象類而不是接口IDBObject會怎麼樣?你應該繼承而不是實現。 抽象類可以定義所需的構造函數。

+0

抽象類可以使用,而我們做泛型...任何張貼或代碼示例? – KoolKabin 2010-06-01 12:58:28

+0

除了可以使用抽象類的接口(在Vb.Net中,關鍵字是MustInherit)。 定義泛型類只能將類型限制爲基類型。這裏的接口與抽象類相同。 – 2010-06-01 13:10:52

+0

儘管這個想法沒有問題,但不能保證實現類將包含所需的構造函數,它可能會向構造函數中添加額外的參數,因此您將無法使用DataRow確保它不會調用構造函數失敗。唯一可以保證的是,對於默認構造函數將存在的類型的'New'約束。 – 2010-06-01 13:16:46