我正在为数学问题创建一个软件。如您所知,有许多类型的数学问题。
在我的软件中,一些问题是从Xml文件(存储库)中获得的,而其他问题可以由工厂生成(随机数,你知道)。
例如,如果我正在创建二进制问题作为补充,如果我选择第一个选项,我可以有一个获取thre文件的类并选择其中一些。或者如果我选择第二个,我可以随机生成问题:
x = random.Next(y, z);
y = random.Next(y, z);
return new BinaryProblem(x, y);
类似的东西。
所以我现在开发了这个设计,我想我已经建立了一个策略模式。
public interface IProblemService
{
IEnumerable<Problem> GetProblems();
}
public class ProblemService : IProblemService
{
private readonly IService service;
public ProblemService(IService service)
{
this.service = service;
}
public IService Service
{
get { return service; }
}
public IEnumerable<Problem> GetProblems()
{
return this.service.GetProblems();
}
}
/* =====================================================*/
CONCRETE CLASSES
public interface IService
{
IEnumerable<Problem> GetProblems();
}
// When I want to generate random problems
public abstract class FactoryService : IService
{
public IEnumerable<Problem> GetProblems();
public abstract Generate();
}
// When I want to get problems through a XML file
public class RepositoryService : IService
{
public abstract IEnumerable<Problem> GetProblems();
void Submit(IEnumerable<Problem> problems);
}
在服务中我把IService作为公共服务器,因为我需要知道服务是工厂还是存储库。如果这是一个存储库,我会向文件提交一些问题。
我不相信这种设计。我想我是多余的,这不是最好的方法。
你能否提出改善意见或想法?
编辑: 我对第一个选项的意思是:
public IEnumerable<Problem> GetProblems()
{
if (model == null)
{
model = new List<Problem>();
// Dummy Data.
model.Add(new SimplifyProblem() { Id = "1", Expression = "8 ÷ 2 x 5 ÷ 10", Result1 = 2 });
model.Add(new SimplifyProblem() { Id = "2", Expression = "20 ÷ 2 x 5 - 2", Result1 = 48 });
model.Add(new SimplifyProblem() { Id = "3", Expression = "15 ÷ 5 + 3", Result1 = 6 });
model.Add(new SimplifyProblem() { Id = "4", Expression = "6 + 4² ÷ 8 - 2", Result1 = 6 });
model.Add(new SimplifyProblem() { Id = "5", Expression = "8 + 2 x 4", Result1 = 40 });
model.Add(new SimplifyProblem() { Id = "6", Expression = "8 + 4 x (5 - 3)", Result1 = 16 });
model.Add(new SimplifyProblem() { Id = "7", Expression = "8 - 3 + 5", Result1 = 10 });
// ...
}
return model;
}
答案 0 :(得分:1)
我不确定为什么你有两个独立的界面,IProblemService
和IService
;对我而言,似乎他们做了同样的事情。
我会将随机问题(“工厂”部分)的生成与实际返回问题的类(“存储库”部分)分开:
public interface IProblemRepository {
IEnumerable<Problem> LoadProblems();
}
public class XmlProblemRepository : IProblemRepository {
...
}
public class InMemoryProblemRepository : IProblemRepository {
private readonly IEnumerable<Problem> problems;
public InMemoryProblemRepository(IEnumerable<Problem> problems) {
this.problems = problems;
}
public IEnumerable<Problem> LoadProblems() {
return problems;
}
}
public class RandomProblemFactory {
public IEnumerable<Problem> GenerateProblems(int count) {
...
}
}
然后您可以从XML文件加载:
repository = new XmlProblemRepository("problems.xml");
或者您可以使用工厂生成问题并从内存存储库中获取它们:
factory = new RandomProblemFactory();
problems = factory.GenerateProblems(10);
repository = new InMemoryProblemRepository(problems);
答案 1 :(得分:0)
看起来你想要有不同的问题来源(Xml文件,数据库,内存),并使你的代码持久性无知。如果是这样,我不会在工厂类中实现IService
接口。保持工厂仅用于随机生成问题。我会在界面中添加Submit
:
public interface IService
{
IEnumerable<Problem> GetProblems();
void Submit(IEnumerable<Problem>);
}
XmlRepositoryService
类将从/向Xml文件获取/保存数据:
public class XmlRepositoryService : IService
{
public IEnumerable<Problem> GetProblems()
{
//get the problems from the Xml file
}
public void Submit(IEnumerable<Problem> problems)
{
//save problems to the xml file
}
}
内存中的存储库类将存储一系列问题:
public class MemoryRepositoryService : IService
{
private List<Problem> problemList = new List<Problem>();
public IEnumerable<Problem> GetProblems()
{
return problemList;
}
public void Submit(IEnumerable<Problem> problems)
{
problemList.AddRange(problems.ToList());
}
}
ProblemFactory
类只有GenerateRandom
方法:
public class ProblemFactory
{
public static Problem GenerateRandom()
{
var x = random.Next(y, z);
var y = random.Next(y, z);
return new BinaryProblem(x, y);
}
}
要使用它,只需实例化一个存储库类,生成一个问题,将其添加到列表中并将列表提交到存储库:
var problems = new List<Problems>();
var problem = ProblemFactory.GenerateRandom();
problems.Add(problem);
var repository = new MemoryRepositoryService(); //or XmlRepositoryService
repository.Submit(problems);