1

假设我有这个接口 IRepository

 public interface IRepository
 {
    #region User
        IUser AddUser(String userName, String password, String email);
        IUser FindUser(String identifier);
    #endregion User

    #region Product
        IProduct AddProduct(...);
        void RemoveProduct(...);
    #endregion Product
}

到目前为止,这是非常基本的,我可以做类似的事情

IRepository MyRepository = new Repository(...);
MyRepository.AddUser(...);
MyRepository.RemoveProduct(...);

理想情况下,我想要类似的东西

public interface IRepository
{
    #region User
        IUser User.User(String userName, String password, String email);
        IUser User.Find(String identifier);
    #endregion User

    #region Product
        IProduct Product.Add(...);
        void Product.Remove(...);
    #endregion Product
}

不幸的是,这在 C# 中不被接受。我无法添加这些前缀。

我想用这种命名空间来写类似这样的东西

IRepository MyRepository = new Repository(...);
MyRepository.User.Add(...);
MyRepository.Product.Remove(...);

我不想将 User 和 Product 对象添加到我的界面中,因为我只需要一种通过这种前缀来改善阅读的方法。

任何想法?

谢谢

4

7 回答 7

3

将其拆分为两个单独的接口。

public interface IRepositoryUser
{
    IUser Add(String userName, String password, String email);
    IUser Find(String identifier);
}

public interface IRepositoryProduct
{
    IProduct Add(...);
    void Remove(...);
}

public interface IRepository
{
    IRepositoryUser User { get; }
    IRepositoryProduct Product { get; }
}
于 2011-03-10T08:48:05.510 回答
1

那么在你刚刚定义的and中定义Add方法IUserRemove方法呢?IProductIRepositoryIUser User {get; set;}IProduct Product {get; set;}

我相信你的语法MyRepository.User.Add(...);MyRepository.Product.Remove(...);很好。

于 2011-03-10T08:50:32.027 回答
1

正如您已经意识到的那样,您想要的在 C# 语法中是不合法的。
我建议你坚持你的第一个版本。它清晰、易读并符合默认命名约定。

于 2011-03-10T08:47:32.730 回答
1

如果您在谈论存储库模式,请回答:

在我看来,根据我的经验,你为什么要混合产品和用户?

为什么要为存储库方法添加前缀?

只需为任何域对象类型“IUserRepository”和“IProductRepository”创建一个存储库,您就不会有这种奇怪的要求。

我不知道您是否在另一种编程语言中具有此功能,但是,即使您有与否,我发现一个糟糕的设计使存储库不仅仅负责域对象类型。


如果您在谈论其他任何事情,请回答

您也需要分离关注点。

例如,您将拥有一项数据服务,并且您想要管理用户和产品。我建议您创建两个管理器:UsersManager 和 ProductsManager。

两者都将与 DataServiceManager 相关联,因此您可以拥有以下内容:

DataServiceManager dataServiceMan = new DataServiceManager();
dataServiceMan.Users.RegisterUser(...);
dataServiceMan.Products.CreateProduct(...);
于 2011-03-10T08:48:57.523 回答
0

我认为在不同的 Repositories 类和基础 IRepository 中执行不同实体的单独逻辑更好,只保留常用方法,例如 Add Remove Save Update 等

interface IRepository
{
   void Save();
   //other common methods
}
interface IProductRepository:IRepository
 {
   //Methods specified for products
 }
于 2011-03-10T08:49:52.417 回答
0

通常使用泛型解决,所以你会有

  interface IRepository<T>

{
   T FindAll()
   T FindSingle(string id)

}

然后基于接口实现派生类,几乎总是让你的接口膨胀,这不是要走的路,会破坏ISP

于 2011-03-10T08:59:54.107 回答
0

我想您需要显式接口实现,如下面的示例:

    ....................
    interface IOne
    {
       void MethodOne();
    }

    interface ITwo
    {
        void MethodTwo();
    }

    interface IThree
    {
        void MethodThree();
    }

    class TestIf : IOne, ITwo, IThree
    {
        void IThree.MethodThree()
        {
            MessageBox.Show("Method three");                
        }

        void IOne.MethodOne()
        {
            MessageBox.Show("Method one");
        }

        void ITwo.MethodTwo()
        {
            MessageBox.Show("Method two");
        }
    }
    ...................
    private void button1_Click(object sender, EventArgs e)
    {
        TestIf t = new TestIf();

        IOne one = t as IOne;
        ITwo two = t as ITwo;
        IThree three = t as IThree;

        one.MethodOne();
        two.MethodTwo();
        three.MethodThree();

    }

请注意,在这种方法中,您只能通过将对象显式转换为指定接口来调用接口方法

于 2011-03-10T09:09:51.540 回答