前言:
好久之前,某个网友提的需求,对商品进行加价,根据原商品的价格不同,加价的方式不同。
具体如下:
250元以下 按比率10%以内加价
251~500 加价 25元以下
501~5000 按比率 5%以内加价
5000以上 加价250元以下
比如某种商品价格是:6000或者10000按照5000元以上的标准调。
分析:
首先,加价是一个范围,因此我们先定义一个结构,PriceRange:
1 public struct PriceRange
2 {
3 public decimal MaxPrice { get; set; }
4 public decimal MinPrice { get; set; }
5 }
对于加价相关的逻辑,有两种,一种为固定加价,一种为按比率加价,因此利用策略模式处理如下(英文类名请无视,硬伤):
1 public interface IPriceStrategy
2 {
3 PriceRange GetPriceRange(decimal purchasePrice);
4 }
5
6 /// <summary>
7 /// 固定加价策略
8 /// </summary>
9 public class FixedPriceStrategy : IPriceStrategy
10 {
11 private decimal _fixedPrice;
12
13 /// <summary>
14 ///
15 /// </summary>
16 /// <param name="fixedPrice">加价金额</param>
17 public FixedPriceStrategy(decimal fixedPrice)
18 {
19 this._fixedPrice = fixedPrice;
20 }
21
22 public PriceRange GetPriceRange(decimal purchasePrice)
23 {
24 return new PriceRange()
25 {
26 MinPrice = purchasePrice,
27 MaxPrice = purchasePrice + _fixedPrice,
28 };
29 }
30 }
31
32 /// <summary>
33 /// 百分比加价策略
34 /// </summary>
35 public class PercentagePriceStrategy : IPriceStrategy
36 {
37 private decimal _percent;
38
39 /// <summary>
40 ///
41 /// </summary>
42 /// <param name="percent">加价率</param>
43 public PercentagePriceStrategy(decimal percent)
44 {
45 this._percent = percent;
46 }
47
48 public PriceRange GetPriceRange(decimal purchasePrice)
49 {
50 return new PriceRange()
51 {
52 MinPrice = purchasePrice,
53 MaxPrice = purchasePrice * (1 + _percent),
54 };
55 }
56 }
最后需要一个工具类,封装相关加价逻辑,并暴漏一个方法出来:
PS:这里设计:每种加价策略的低价作为key,放到字典中。 获取加价区间时,取小于或等于 传入价格的所有Key中最大的一个(如果没有,则取最大的Key),即为最终的加价策略!
这样设计的好处:可以避免大量的if 和else if 。。。
1 public class PriceUtility
2 {
3 /// <summary>
4 /// 相关加价策略
5 /// </summary>
6 private static Dictionary<decimal, IPriceStrategy> Dic = new Dictionary<decimal, IPriceStrategy>();
7
8 static PriceUtility()
9 {
10 //初始化加价规则(todo:这里是写死的,如果需求多变,也可以从外部存储获取并初始化)
11 Dic.Add(0, new PercentagePriceStrategy(0.1m));
12 Dic.Add(250, new FixedPriceStrategy(25));
13 Dic.Add(500, new PercentagePriceStrategy(0.05m));
14 Dic.Add(5000, new FixedPriceStrategy(250));
15 }
16
17 /// <summary>
18 /// 获取加价区间
19 /// </summary>
20 /// <param name="purchasePrice"></param>
21 /// <returns></returns>
22 public static PriceRange GetRange(decimal purchasePrice)
23 {
24 var key = GetCurrentKey(purchasePrice);
25
26 return Dic[key].GetPriceRange(purchasePrice);
27 }
28
29 /// <summary>
30 /// 获取符合条件的Key
31 /// </summary>
32 /// <param name="purchasePrice"></param>
33 /// <returns></returns>
34 private static decimal GetCurrentKey(decimal purchasePrice)
35 {
36 //找到小于等于该价格的所有Key
37 var keys = Dic.Keys.Where(r => r.CompareTo(purchasePrice) <= 0).ToArray();
38 //如果没有,则取最大的
39 if (keys.Length == 0) return Dic.Keys.Max();
40 //有则在找到的Key中取最大的
41 return keys.Max();
42 }
43 }
结果:
用控制台应用程序测试一下:
1 static void Main(string[] args)
2 {
3 ConsolePriceRange(100);
4 ConsolePriceRange(240);
5 ConsolePriceRange(250);
6 ConsolePriceRange(490);
7 ConsolePriceRange(500);
8 ConsolePriceRange(4900);
9 ConsolePriceRange(5000);
10 ConsolePriceRange(10000);
11
12 Console.ReadKey();
13 }
14
15 static void ConsolePriceRange(decimal price)
16 {
17 PriceRange range = PriceUtility.GetRange(price);
18
19 Console.WriteLine("产品价格{0}的加价区间为:{1}~{2}", price, range.MinPrice, range.MaxPrice);
20 }

