C# 我是否从服务传递代码以进行进一步处理?

C# 我是否从服务传递代码以进行进一步处理?,c#,.net,service,solid-principles,C#,.net,Service,Solid Principles,这里的学生,我真的试着用谷歌搜索这个可能很简单的问题,但找不到一个好的答案,也许我只是不知道谷歌的正确术语,如果是这样,我很抱歉 我试图找出在服务接收到数据后将JSON字符串向前传递到系统中的最佳实践,例如传递到解析器中,然后继续处理对象 今天,我们学习编写服务的方式,函数可能是这样的 private void ReceiveData(string json) { var parser = new JsonParser(); var normalizer = new Normal

这里的学生,我真的试着用谷歌搜索这个可能很简单的问题,但找不到一个好的答案,也许我只是不知道谷歌的正确术语,如果是这样,我很抱歉

我试图找出在服务接收到数据后将JSON字符串向前传递到系统中的最佳实践,例如传递到解析器中,然后继续处理对象

今天,我们学习编写服务的方式,函数可能是这样的

private void ReceiveData(string json)
{
    var parser = new JsonParser();
    var normalizer = new Normalizer();
    var dataHandler = new DataHandler();

    var data = normalizer.Normalize(parser.Parse(json));
    dataHandler.Handle(data);
}
但在我看来,这似乎违反了单一责任原则,因为现在它不仅被设置为接收数据,而且还被解析、规范化和处理。这是正确的方法吗?因为我觉得这样做不对


//攻击Betty在我看来,是的,您的代码违反了单一责任,因为如果您需要更改逻辑,如果

  • 您希望更改为使用另一个json解析器
  • 您想更改接收数据逻辑
我很难向您推荐一种正确的重构方法,因为它缺少关于项目性质、类型、体系结构等的大量信息。然而,最简单的方法是将json解析器逻辑放在其他地方

示例:我更喜欢在这里使用字符串扩展方法

//StringExtension.cs
public static class StringExtension {
    public static string ToJson(this string input)  {
        var parser = new JsonParser();
        var normalizer = new Normalizer();
        var dataHandler = new DataHandler();

        return normalizer.Normalize(parser.Parse(json));
    }
}

// in your class
private void ReceiveData(string json)
{
    dataHandler.Handle(json.ToJson());
}

我不同意kienct89,进一步破坏这种方法是过分的。方法的职责是接收数据,但方法中的所有操作都属于接收数据的类别

您可以通过声明用于数据解析的接口来分解该类

public interface IDataParser
{
    string ParseData(string input);
}
然后,您可以创建实现此接口的数据处理程序和JSON数据解析器

public class JsonDataParser : IDataParser
{
    public string ParseData(string input)
    {
        //Convert the input to JSON.
    }
}

public class DataHandler
{
    private IDataParser _parser;

    public DataHandler(IDataParser parser)
    {
        _parser = parser;
    }

    public void ReceiveData(string data)
    {
        //Convert the data to the desired format.
        string result = _parser.ParseData(data);
    }
}
这种方法的思想是,通过使用接口编程,您的数据处理程序类不再与解析数据的特定实现绑定。也许将来您可能希望将数据解析为CSV格式,而不是JSON格式,在这种情况下,您只需为数据处理程序提供不同的解析器实现

下面是一个示例用法:

JsonDataParser jsonParser = new JsonDataParser();
DataHandler myDataHandler = new DataHandler(jsonParser);

myDataHandler.ReceiveData("Le toucan has arrived.");
正如我前面提到的,
DataHandler
与特定的实现无关,因此您可以传入一个
CsvDataParser
,而无需更改
DataHandler
中的任何内容


无论如何,我仍然认为这有点过分了。当然,这有助于您的代码更好地适应不断变化的需求,如果您愿意的话,也会更灵活。然而,对于您所需要的,我相信您当前的方法完全符合要求。

示例代码违反了坚实的设计原则;然而,我关心的不是单一责任原则,而是依赖倒置原则。服务应该将其三个依赖项(
JsonParser
Normalizer
DataHandler
)注入其中,而不是自己实例化它们


请注意,依赖项反转可能不是本课程的目的,因此为了简单起见,可能省略了它。

当一个方法使用另一个方法时,不能说它在做另一个方法的工作,因为实现是抽象的。这同样适用于对象协作。这里唯一明显的缺陷是没有使用依赖项反转(collaborator对象是硬编码的)。