6

我正在学习 C#,并试图弄清楚什么时候使用类,什么时候不使用。

如果我正在为银行编写应用程序,我知道我会为客户使用类,其中包括他们的姓名、帐号、余额等。我会为将存款存入他们的账户、取款、更改的方法使用静态类吗?他们的地址等,因为我只需要写一次?

另外,我将使用什么来跟踪每个客户对象?拥有 2,000 名客户:

exampleName = new Customer();

在我的代码中似乎不正确。我还没到学习数据库的地步,只是在学习课程。

4

6 回答 6

5

拥有一个数据库将是理想的,但同时您可以使用 IEnumerable 来保存您的 Customer 对象,如下所示:

List<Customer> myCustomers = new List<Customer>();
myCustomers.Add(new Customer {Name = "Bob", Address = "123 Anywhere St." });  

然后你可以在需要的地方传递列表。

通常,您将在Customer拥有帐户的类上拥有一个属性:

public class Customer
{
    public Customer()
    {
        _accounts = new List<Account>();
    }

    public List<Account> Accounts 
    {
        get { return _accounts; }
        set { _accounts = value; }
    }

    private List<Account> _accounts;
}

等等。请注意,当您是初学者时,我会保持这种简单性并以更冗长和描述性的方式来做事。

以这种方式使用项目列表是一个很好的开始方式,因为当您开始使用数据库时,您会自然而然地使用它们;您将从数据库中检索结果集,然后将这些结果集转换为业务对象列表。

至于使用静态方法做业务逻辑,比如调整余额、更改地址等,对于现阶段的你来说无所谓。如果您使用的是 Resharper 之类的工具,它会用类似的建议来唠叨您,但在您的情况下,您可以放心地忽略那个特定的工具。您应该寻找的是尽可能保持一切自包含,避免数据泄漏和对象之间的责任泄漏 - 这只是良好的编码规则,也是防止由松散编码引起的错误的好方法。

一旦你确定了你的功能并开始工作,你可能希望将一些功能移动到静态的“帮助”样式类中。这绝对没问题,但要小心 - 辅助类很棒,如果你不遵守编码规则,一切都会很快变成反模式。

于 2012-10-13T02:38:24.440 回答
3

您无需使用静态类或静态方法,只需编写一次方法。这样做可能有意义,也可能没有意义,但这是编写方法而无需重复自己的一种完全有效的方式:

public class Customer
{
    //properties, constructors, etc.

    public virtual void Deposit(decimal amount) { }
    public virtual void Withdraw(decimal amount) { }
    //etc
}

这也允许您利用多态性,例如

public class BusinessCustomer : Customer
{
    public override void Deposit(decimal amount) { //some other implementation }
}
于 2012-10-13T02:42:08.697 回答
1

当您不打算实例化对象时使用静态类。你得到了那个类的一个“实例”——你不能做这样的事情:

MyStaticClass m = new MyStaticClass();
m.SomeFunc();

当你有一个静态类时。相反,您可以通过使用类名本身来使用它。就像是:

MyStaticClass.SomeFunc();

至于您将使用什么来跟踪每个 Customer 对象?您可以使用某种集合来保存这些。诚然,在一个真实的系统中,会有某种持久性部件,可能是一个数据库,来保存数据。但是你可以做一些类似的东西:

IEnumerable<Customer> Customers = new List<Customer>();

然后将您的客户添加到该列表中

Customers.Add(new Customer() { ... });

回到关于静态方法的问题......

因此,这里的交易是您不会在静态方法中引用实例成员,因此您不会使用静态方法来更新特定客户的地址。假设您的 Customer 类看起来像:

public class Customer
{
   public string Address { get; set; }
}

你不能使用像这样的静态方法

public static void SetAddress()

因为每个客户(大概)都有不同的地址。您无法访问那里的客户地址,因为它不是静态的。懂吗?相反,如果您想做一些不需要处理实例数据的事情,您将使用静态方法。我将静态方法用于实用程序功能之类的东西。

public static double ComputeSomething(double someVal) { ... }

在这里,任何人都可以调用 ComputeSomething 函数,例如:

var result = MyStaticClass.ComputeSomething(3.15);

这里的要点是静态不用于实例化对象,而是将它们真正用作保存函数的方便容器。静态函数可以在非静态类上但不能访问任何实例数据的函数。

使用静态函数的一个地方是单例模式。您将构造函数设置为非公开的,因此人们无法调用它,而是在类上提供一个静态方法来返回该类的唯一实例。就像是:

public class MySingleton
{
   private static MySingleton instance;

   private MySingleton() {}

   public static MySingleton Instance
   {
      get 
      {
         if (instance == null)
         {
            instance = new MySingleton();
         }
         return instance;
      }
   }
}
于 2012-10-13T02:46:08.900 回答
0

取款,存款等

那些将被称为Transactions

于 2012-10-13T02:44:05.823 回答
0

这是对其他答案的补充。这是具有接口的多态性的示例。

public interface IDeposit {
    void Deposit(decimal amount);
}

public interface IWithdraw {
    void Withdraw(decimal amount);
}

public class Customer : IDeposit, IWithdraw {
    public void Deposit(decimal amount) { throw new NotImplementedException(); }
    public void Withdraw(decimal amount) { throw new NotImplementedException(); }
}

public class DepositOnlyATM : IDeposit {
    public void Deposit(decimal amount) { throw new NotImplementedException(); }
}

保持概念分离,并允许实现多个接口,或者只实现一个。使用类继承方法,您只会得到一种,而您会得到全部。根据我的经验,你不可避免地会以意大利面结束,因为子类想要一些行为,但不是全部。

于 2012-10-13T02:52:10.860 回答
0

我建议您首先为您的银行示例写一些简单的用户故事,而不是立即进入实施细节。例如

  1. 作为客户,我想开一个新账户,以便进行存款和取款

正是在这个要求中,我们可以设想几个类(客户和帐户)。从那里只是在功能上分解客户应该做什么以及帐户应该做什么。

我发现“面向对象的思维过程”这本书是一本很好的读物,将有助于回答一些关于“我什么时候做这个和那个”的问题。

祝好运并玩得开心点!

于 2012-10-13T10:27:42.413 回答