这是个新手小白写的博客。
背景:
最近撸码的时候总是感觉自己写的特别乱。十分苦恼。大神建议我看看设计模式。于是找来一本《大话设计模式》的书来看,听说评价非常不错。
来看看我的收获吧。
内容:
首先研究的是简单工厂模式。我实现了一遍书上的实例(控制台应用程序写的),如下
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Text.RegularExpressions;
/// <summary>
/// 实现大话设计模式中的简单工厂实例
/// 此脚本实现的功能是:输入两个数字和运算符号,得到结果
/// </summary>
namespace TestCode
{
class Program
{
//客户端的代码
static void Main(string[] args)
{
//用户输入
string numberA = write("请输入第一个数字:\n");
while (!IsFloat(numberA))
{
numberA = write("您输入的\"" + numberA + "\"不是数字无法运算,请输入第一个数字:\n");
}
string markStr = write("请输入一个运算符号:\n");
while (!IsSymbol(markStr))
{
markStr = write( "您输入的\""+ markStr + "\"运算符不在本程序中,请输入[加、减、乘、除]中的一个:\n");
}
string numberB = write("请输入第二个数字:\n");
while (!IsFloat(numberB))
{
numberB = write("您输入的\"" + numberB + "\"不是数字无法运算,请输入第二个数字:\n");
}
//创建工厂对象
Operation operation = OperationFactroy.CreateOperation(markStr);
operation.NumberA = Convert.ToDouble(numberA);
operation.NumberB = Convert.ToDouble(numberB);
double result = operation.GetResult();
//输出结果
write("运算结果是:" + result);
}
static string write(string str)
{
Console.Write(str);
return Console.ReadLine();
}
/ <summary>
/ 判断是不是整数(正整数、负整数、零)
/ true:是整数 false:不是整数
/ </summary>
//public static bool IsNumber(string str)
//{
// Regex reg = new Regex("^(0|-?[1-9][0-9]*)$");
// Match ma = reg.Match(str);
// return ma.Success;
//}
/// <summary>
/// 判断是不是浮点数(正浮点数、负浮点数、零)
/// true:是整数 false:不是整数
/// //参考 https://www.cnblogs.com/codeabc/p/3386641.html
/// </summary>
public static bool IsFloat (string str)
{
Regex reg = new Regex("^(-?\\d+)(\\.\\d+)?$");
Match ma = reg.Match(str);
return ma.Success;
}
/// <summary>
/// 是不是支持的运算符
/// </summary>
/// <param name="str"></param>
/// <returns></returns>
public static bool IsSymbol(string str)
{
return OperationFactroy.OperationFactroyDic().ContainsKey(str);
}
}
}
/// <summary>
/// 简单工厂类
/// 实现:输入的两个数和结果的接口
/// </summary>
public class Operation
{
private double numberA = 0;
private double numberB = 0;
//输入的第一个数字
public double NumberA
{
get { return numberA; }
set { numberA = value; }
}
//输入的第二个数字
public double NumberB
{
get { return numberB; }
set { numberB = value; }
}
//输出的结果
public virtual double GetResult()
{
double result = 0;
return result;
}
}
/// <summary>
/// 加法工厂
/// 实现:加法运算,输出结果
/// </summary>
class OperationAdd : Operation
{
public override double GetResult()
{
double result = 0;
result = NumberA + NumberB;
return result;
}
}
/// <summary>
/// 减法工厂
/// 实现:减法运算,输出结果
/// </summary>
class OperationSub : Operation
{
public override double GetResult()
{
double result = 0;
result = NumberA - NumberB;
return result;
}
}
/// <summary>
/// 乘法工厂
/// 实现:乘法运算,输出结果
/// </summary>
class OperationMul : Operation
{
public override double GetResult()
{
double result = 0;
result = NumberA * NumberB;
return result;
}
}
/// <summary>
/// 除法工厂
/// 实现:除法运算,输出结果
/// </summary>
class OperationDic : Operation
{
public override double GetResult()
{
double result = 0;
if (NumberB == 0)
{
throw new Exception("除数不能为0。");
}
result = NumberA / NumberB;
return result;
}
}
/// <summary>
/// 分类工厂类
/// 实现:接受一个符号输入,返回一个算法工厂
/// </summary>
public class OperationFactroy
{
//==============================自己改的,主要考虑输入运算符的判断=================================
public static Dictionary<string, Operation> OperationFactroyDic()
{
Dictionary<string, Operation> operationFactroyDic = new Dictionary<string, Operation>();
operationFactroyDic.Add("+", new OperationAdd());
operationFactroyDic.Add("-", new OperationSub());
operationFactroyDic.Add("*", new OperationMul());
operationFactroyDic.Add("/", new OperationDic());
return operationFactroyDic;
}
public static Operation CreateOperation(string operate)
{
Operation oper = OperationFactroyDic()[operate];
return oper;
}
//==============================自己改的,主要考虑输入运算符的判断=================================
/* 大化设计模式上的实例
* public static Operation CreateOperation(string operate)
* {
* Operation oper = null;
* switch (operate)
* {
* case "+":
* oper = new OperationAdd();
* break;
* case "-":
* oper = new OperationSub();
* break;
* case "*":
* oper = new OperationMul();
* break;
* case "/":
* oper = new OperationDic();
* break;
* }
* return oper;
* }
*/
}
理解、总结:
以上是自己根据书上的实例实现的简单工厂——计算器。
首先我觉得简单工厂模式,就是建造一个总类(共同属性的类)->然后实现各自算法的子类->判断运用算法的类->客户端调用就完成了。
主要解决了对象创建的问题。我感觉这样的代码设计还是有点美中不足。也就是说:如果我的算法需求增加了,我得重新增加算法,先写一个集成的子类,然后分类器中增加判断。觉得很麻烦。继续研究。。。