【问题标题】:C# design related query (better refactoring)C#设计相关查询(更好的重构)
【发布时间】:2017-03-01 11:33:24
【问题描述】:

我正在开发一个我觉得有改进空间的功能。

场景:

我在物理仪器中有不同类型的按钮。每种按钮类型都有特定的功能(比如提高音量或降低音量等)。

我有一个任务要实现 - 根据某些操作(短按、中按和长按)获取新按钮类型的功能。我遵循了用于获取其他按钮类型功能的方法。

最终结果:

最终结果应该是新的按钮类型类应该返回按钮支持的所有功能。

实施:

我创建了一个继承自“InstrumentButtonBase”的类“InstrumentButtonType4”。

"InstrumentButtonType4" 类有一个方法 GetButtonTypeFunctionalities(),它首先检查 如果按钮可用并启用。

然后根据操作添加按钮功能。

现在我有短按、长按和中按三种动作。

主要逻辑:-

我为每个操作“int shortPress = _instrumenrData.GetValue(3);”获取存储在仪器中的当前值并调用静态映射器“InstructionButtonFunctionalityMapper " 以获取映射到给定 "shortPress" 值的相应功能。

想以更好的方式重构

如果能写得更好,我想改进这三个方法

  1. AddFunctionalityForShortPress()
  2. AddFunctionalityForMediumPress()
  3. AddFunctionalityForVeryLongPress()

这三种方法中的逻辑能不能写成更好的设计。我们能否以某种方式消除 Mapper 并使 实现更简单/灵活且可扩展?

我在下面粘贴了整个课程代码。 代码可以在控制台应用程序中编译。 您的专家建议将真正帮助我以更好的方式学习和实现这一目标。

public interface IInstrumentData
{
    int GetValue(int location);
}

public abstract class InstrumentButtonBase
{
   public abstract  bool IsAvailable();
   public  abstract bool IsEnable();

   public abstract IDictionary<ButtonType, IDictionary<ButtonAction, ButtonFunctionality>> GetButtonTypeFunctionalities();
}


public class InstrumentButtonType4 : InstrumentButtonBase
{
    private readonly IInstrumentData _instrumenrData;

    public InstrumentButtonType4(IInstrumentData instrumenrData)
    {
        _instrumenrData = instrumenrData;
    }

    public override IDictionary<ButtonType, IDictionary<ButtonAction, ButtonFunctionality>> GetButtonTypeFunctionalities()
    {
        var instrumentMaps = new Dictionary<ButtonType, IDictionary<ButtonAction, ButtonFunctionality>>();
        var buttonFunctionality = new Dictionary<ButtonAction, ButtonFunctionality>();

        if (!IsAvailable() && !IsEnable())
        {
            return instrumentMaps;
        }

        AddButtonFunctionality(buttonFunctionality);
        instrumentMaps.Add(ButtonType.Volume, buttonFunctionality);

        return instrumentMaps;
    }

    private void AddButtonFunctionality(Dictionary<ButtonAction, ButtonFunctionality> buttonFunctionality)
    {
        AddFunctionalityForShortPress(buttonFunctionality);
        AddFunctionalityForMediumPress(buttonFunctionality);
        AddFunctionalityForVeryLongPress(buttonFunctionality);
    }

    private void AddFunctionalityForVeryLongPress(Dictionary<ButtonAction, ButtonFunctionality> buttonFunctionality)
    {
        // Get v
        int veryLongPress = _instrumenrData.GetValue(1); // gets the data from the instrument itself

        // calls mapper to get the corresponding functionality
        ButtonFunctionality functionality = InstructionButtonFunctionalityMapper.Mapper["InstrumentButtonType1" + veryLongPress];
        buttonFunctionality.Add(ButtonAction.ShortPress, functionality);
    }

    private void AddFunctionalityForMediumPress(Dictionary<ButtonAction, ButtonFunctionality> buttonFunctionality)
    {
        int mediumPress = _instrumenrData.GetValue(2); // gets the data from the instrument itself

        // calls mapper to get the corresponding functionality
        ButtonFunctionality functionality = InstructionButtonFunctionalityMapper.Mapper["InstrumentButtonType1" + mediumPress];
        buttonFunctionality.Add(ButtonAction.MediumPress, functionality);
    }

    private void AddFunctionalityForShortPress(Dictionary<ButtonAction, ButtonFunctionality> buttonFunctionality)
    {
        int shortPress = _instrumenrData.GetValue(3); // gets the data from the instrument itself

        // calls mapper to get the corresponding functionality
        ButtonFunctionality functionality = InstructionButtonFunctionalityMapper.Mapper["InstrumentButtonType1" + shortPress];
        buttonFunctionality.Add(ButtonAction.ShortPress, functionality);
    }

    public override bool IsAvailable()
    {
        // checks some logic and returns tru or false
        return true;
    }

    public override bool IsEnable()
    {
        // checks some logic and returns tru or false
        return true;
    }
}

public static class InstructionButtonFunctionalityMapper
{
    private static Dictionary<string, ButtonFunctionality> _mapper;
    public static Dictionary<string, ButtonFunctionality> Mapper
    {
        get
        {
            return _mapper ?? (_mapper = FillMapper());
        }
    }

    private static Dictionary<string, ButtonFunctionality> FillMapper()
    {
        var mapper = new Dictionary<string, ButtonFunctionality>
        {
            {"InstrumentButtonType1" + "VeryLongPress" + "0", ButtonFunctionality.DoAction1},
            {"InstrumentButtonType1" + "VeryLongPress" + "1", ButtonFunctionality.DoAction2},
            {"InstrumentButtonType1" + "VeryLongPress" + "2", ButtonFunctionality.DoAction3},
            {"InstrumentButtonType1" + "0", ButtonFunctionality.ProgramDown},
            {"InstrumentButtonType1" + "1", ButtonFunctionality.ProgramUp},
            {"InstrumentButtonType1" + "2", ButtonFunctionality.VolumeDown},
            {"InstrumentButtonType1" + "3", ButtonFunctionality.VolumeUp},
            {"InstrumentButtonType1" + "4", ButtonFunctionality.DoAction1},
            {"InstrumentButtonType1" + "5", ButtonFunctionality.DoAction4},
            {"InstrumentButtonType1" + "6", ButtonFunctionality.DoAction5}
        };


        return mapper;
    }
}

public enum ButtonFunctionality
{
    VolumeUp,
    VolumeDown,
    ProgramUp,
    ProgramDown,
    DoAction1,
    DoAction2,
    DoAction3,
    DoAction4,
    DoAction5
}

public enum ButtonAction
{
    ShortPress,
    MediumPress,
    LongPress,
}

public enum ButtonType
{
    PushButton,
    Volume
}

非常感谢!!

【问题讨论】:

标签: c#


【解决方案1】:
  1. 尽量避免使用 1,2 等“幻数”。改用枚举或常量。
  2. 尝试使用显式枚举值,例如 ShortPress = 0 ... 这样代码更具可读性。
  3. “InstrumentButtonType1”应该是常数。
  4. AddFunctionalityForMediumPress、AddFunctionalityForShortPress... 具有相同的行为。更好的方法是创建一种方法 AddFunctionalityForPress 并将不同的值作为参数。
  5. AddButtonFunctionality、AddFunctionalityForShortPress 将这些方法作为扩展方法。然后你可以看到 buttonFunctionality.AddButtonFunctionality(short).AddButtonFunctionality(long) ... 等逻辑序列。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-02-07
    • 1970-01-01
    • 1970-01-01
    • 2011-02-20
    • 1970-01-01
    • 1970-01-01
    • 2011-04-01
    相关资源
    最近更新 更多