2013-01-31 53 views
2

我不知道如何正確管理C#中的接口。我的目標是爲我的業務層服務創建一個抽象類,它具有一些調用不同DAL存儲庫方法的常用方法(如Save(),Dispose())。我想避免在我所有的服務類似重複:C#接口實現

public Save() 
{ 
    repository.Save(); 
} 

我有類似的情景:

接口

namespace Common 
{ 
    public interface IRepository 
    { 
     void Save; 
     void Dispose; 
    } 
} 

DAL

namespace DAL 
{ 
    public Repository : IRepository 
    { 
     public void Save() {}; 
     public void Dispose() {}; 
     public void Add() {} 
    } 
} 

BL

namespace BL 
{ 
    public abstrac BaseService 
    { 
     protected IRepository repository; 
     protected BaseService(IRepository repo) 
     { 
      repository = repo; 
     } 

     public Save() 
     { 
      repository.Save(); 
     } 
    } 

    //... 

    //Tentative 1 
    public Service : BaseService 
    { 
     private Repository rep; 

     public Service() 
      : base(new DAL.Repository()) 
     { 
      rep = base.repository; // ERROR: cannot convert IRepository to Repository 
     } 
    } 
} 

我也試過這樣:

//Tentative 2 
public Service : BaseService 
{ 
    private IRepository rep; 

    public Service() 
     : base(new DAL.Repository()) 
    { 
     rep = base.repository; // OK 
    } 

    public void Add() 
    { 
     rep.Add() // ERROR: IRepository doesn't contain a definition for 'Add' 
    } 
} 

我知道我可以在接口定義所有我想要使用的方法,但我將不得不管理很多問題與泛型類型,正如你應該從我瞭解的問題,我在C#相當新的,我希望能避免複雜性是可能的,utill我會更加的專家至少:)

+0

因爲(我剛剛更新了這篇文章)我想在基類中包裝一些基本上相同的Saves()方法,但是引用了不同的DAL存儲庫..希望你能理解我..我對C#和英語都有問題;) – Davide

回答

1
public Service() 
     : base(new DAL.Repository()) 
    { 
      rep = (Repository)base.repository; 

    } 

這樣你將得到Add()服務,它不是IRepository的一部分,而是擴展類中的一個更新的實現。

+0

我很慚愧我的問題..這很容易!可能我向谷歌提出了錯誤的問題..非常感謝你 – Davide

+1

答案解決了你的問題(雖然沒有異常處理 - 可以使用as或is來檢查你在IRepository中傳遞的是否是一個Repository),但它是一種打破了我認爲你想要首先注入接口的想法。您可能會更好地向IRepository添加'添加',或者可能重新考慮您的設計。 – Cashley

+0

那麼在正確的道路上,沒有什麼是恥辱的。除了我會以演員的方式去做。我想你會明白你什麼時候製作更多的信息庫。現在,因爲你只有一個IRepository的實現,一切似乎都可以。當你實現IRepository 4-5次時,你會看到這個設計的錯誤。 – user1974729

3

首先我覺得你有一個名稱衝突與您成員 IRepository rep.

嘗試使用 DAL.IRepository rep

,你得到一個錯誤的原因是,你定義「添加」爲「倉庫」特有的東西。你的成員變量是一個「IRepository」,允許你將任何實現「IRepository」的東西放到它上面。

僅僅因爲您可以將存儲庫放入其中,並不意味着它上面的所有內容都將成爲存儲庫。 (認爲​​它看起來不錯,手指和拇指,所有的拇指都是手指,但不是所有的手指都是拇指)

如果您需要調用添加任何存儲庫,然後將其添加到接口。否則,您需要確定該成員是否應該是IRepository或Repository。

或者,你可以使用

Repository myRep = rep as Repository; 
    if(rep!=null) 
    { 
     myRep.Add(); 
     ... 
     profit(); 
    } 
0

鑑於你的主要問題是缺乏無障礙的Add方法,並看到,因爲這是一個相對常見的方法,無論如何,我會首先推薦它添加到您的IRepository,所以它看起來是這樣的:

public interface IRepository 
{ 
    void Add(); 
    void Save(); 
    void Dispose(); 
} 

你會再實現你適當的資源庫,同時從IRepository繼承。現在,可以理解你可能想要訪問Repository上的自定義方法。爲了解決這個你可以做的是有你的BaseService接受一個通用存儲庫:

public BaseService<T> where T : IRepository 
{ 
    protected T repository { get; set; } 
    protected BaseService(T repo) 
    { 
     repository = repo; 
    } 
} 

然後服務應該是這樣的

public UserService : BaseService<UserRepository> 
{ 
    public UserService() : base(new DAL.UserRepository()) 
    { 
     // base.Repository is now a UserRepository. 
    }  
} 

使用這種實現您的UserService將能夠訪問所有UserRepository公開的方法,因爲它是強類型的泛型。希望這可以幫助。