特定于客户的方法:
我尝试重构一个代码,其中有很多特定客户的逻辑:
public void SendDocumentsToCustomer(List<Case> cases)
{
foreach(var case in cases)
{
if(case.CustomerId==123)
{
if(case.Type==1 || case.Type==2)
{
SendDocumentsToCustomer123(case)
}
else if(case.CustomerId==456)
{
if(case.Type==1 || case.Type==3)
{
SendDocumentsToCustomer456(case);
}
}
else if(case.CustomerId==768)
{
if(case.Type==2)
{
SendDocumentsToCustomer456(case);
}
else
{
SendDocumentsToCustomer(case);
}
}
}
特定客户的列表将会增长,条件也将被修改。我将有一个通用的解决方案,但也许像这样的方法DoItForClient123不是一个糟糕的解决方案,我应该这样,并以这种方式引入像CanDocumentsBeSendToClient123等方法?
我将非常感谢一些输入
答案 0 :(得分:1)
为了区分每个特定客户的逻辑,我会使用这样的代码:
abstract class DocumentSender //Base class for all document sending components
{
public abstract bool CanSend(Case @case); // Check if sender can send the document
public abstract void SendDocument(Case @case); // Send the document
}
class DefaultDocumentSender : DocumentSender
{
public override bool CanSend(Case @case)
{
return true; //Can process all requests
}
public override void SendDocument(Case @case)
{
// Do something
}
}
class Customer123DocumentSender : DocumentSender
{
public override bool CanSend(Case @case)
{
return @case.CustomerId == 123; //Specific case
}
public override void SendDocument(Case @case)
{
if(@case.Type==1 || @case.Type==2)
{
// Do something different
}
}
}
//Separate class for getting the correct sender
class CaseSenderFactory
{
readonly List<DocumentSender> _senders = new List<DocumentSender>();
public DocumentSenderFactory()
{
//Initialize the list of senders from the most specific.
_senders.Add(new Customer123DocumentSender());
// Add more specific cases here
_senders.Add(new DefaultDocumentSender()); //Last item should be the default sender
}
public DocumentSender GetDocumentSender(Case @case)
{
//At least one sender needs to satisfy the condition
return _senders.First(x => x.CanSend(@case));
}
}
然后您可以使用这样的发件人:
var factory = new DocumentSenderFactory();
foreach(var @case in cases)
{
var sender = factory.GetDocumentSender(@case);
sender.SendDocument(@case);
}
答案 1 :(得分:0)
我认为制作这样的东西是一个很好的想法: 如果代码确实特定于某些客户,则可以为他们创建一个类。如果特定客户的代码以某种方式相关但以不同的方式组合,那么你应该在DecoratorPattern上获取一个战利品(mabye it help)
class Customer
{
public abstract SendDocumentsTo(Customer c);
}
class SpecificCustomerA
{
public overwrite SendDocumentsTo(Customer c)
{
if (c is SpecificCustomerB)
{
//Logic here
}
}
}
class SpecificCustomerB { ... }