(先行DIフレームワークに)依存反転とアーキテクチャ

罪を犯しました:

私は多分、私はいくつかのポイントを欠けている、建築といくつかの問題をしたDI Iを勉強しています。

私は、この非DIのコードを持っていると仮定し(私は、ファイルから「人」のリストを読みます)

static void Main()
{
   PersonReaderFromFile personReader = new PersonReaderFromFile("path-to-file");
   Person p = personReader.GetNext();  //return a Person parsed from file line or NULL at EOF
}

class Person 
{
    //stuffs here
}

class PersonReaderFromFile
{
    public Person GetNext()
    {
        Person person = new Person();
        //some logic
        return person;
    }
}

私がやるので、まず、DIパターンを実現するために、私は、インターフェイスが必要

static void Main()
{
   iPersonReader personReader = new PersonReaderFromFile("path-to-file");
   iPerson p = personReader.GetNext();
}

interface iPerson
{
}

class Person : iPerson
{
}

interface iPersonReader
{
    iPerson GetNext();
}

class PersonReaderFromFile : iPersonReader
{
    public iPerson GetNext()
    {
        Person person = new Person();
        //some logic
        return person;
    }
}

そして今、私の問題:PersonReaderFromFileは人の実装に依存します。大丈夫です?それとも私がPersonFactoryのように、余分なクラスが必要?

static void Main()
{
    iPersonFactory factory = new PersonFactory();
    iPersonReader personReader = new PersonReaderFromFile("path-to-file", factory);
    iPerson person = personReader.GetNext();
}

interface iPerson
{
}

class Person : iPerson
{
}

interface iPersonReader
{
    iPerson GetNext();
}

class PersonReaderFromFile : iPersonReader
{
    iPersonFactory _factory;

    public PersonReaderFromFile(iPersonFactory factory)
    {
        _factory = factory;
    }

    public iPerson GetNext()
    {
        Person person = _factory.CreateNewPerson();
        //some logic
        return person;
    }
}

interface iPersonFactory 
{
    iPerson CreateNewPerson();
}

class PersonFactory : iPersonFactory
{
    iPerson CreateNewPerson()
    {
        Person person = new Person();
        return person;
    }
}

今PersonFactoryは人の実装に依存しますが、それは正しいはずです。何かアドバイス?すべてのTNX。

編集:私は、サンプルPersonReaderFromFile実装を示し、

class PersonReaderFromFile
{
    StreamReader _fileReader;

    public PersonReaderFromFile(string path)
    {
        _fileReader = new StreamReader(file);
    }

    public Person GetNext()
    {
        string line = _fileReader.ReadLine();
        if (line == null)
        {
                _fileReader.Close();
                return null;
        }

       string name, lastName, email;
       ParseInformationFromLine(line, out name, out lastName, out email);

       Person p = new Person { Name = name, LastName = lastName, Email = email };

       return p;
    }

   private ParseInformationFromLine(string line, out string name, out string lastName, out string email)
   {
        //I don't think that matters
   }
}
Nkosi:

PersonReaderFromFile依存しませんPersonそのクラスは、実行時データを表しちょうどPOCOように見えます。

PersonReaderFromFile依存しているStreamReaderとともにParseInformationFromLine機能

自分の関心事にそれらの実装の詳細アウトまず抽象的。

public interface IReadLines {
    string ReadLine();
}

public interface IParsePersonInformationFromLine {
    void ParseInformationFromLine(string line, out string name, out string lastName, out string email);
}

ターゲットクラスは、明示的に抽象化に依存するであろう

public class PersonReaderFromFile {
    private readonly IReadLines reader;
    private readonly IParsePersonInformationFromLine parser;

    public PersonReaderFromFile(IReadLines reader, IParsePersonInformationFromLine parser) {
        this.reader = reader;
        this.parser = parser;
    }

    public Person GetNext() {
        string line = reader.ReadLine();
        if (line == null) {
            return null;
        }

        string name, lastName, email;
        parser.ParseInformationFromLine(line, out name, out lastName, out email);

        Person p = new Person { Name = name, LastName = lastName, Email = email };

        return p;
    }
}

個々の抽象化は、実行時に使用される所望の機能性を満たすために、独自の実装を持っているでしょう。たとえば、読者は内部でまだ使用するStreamReaderラインを取得します。PersonReaderFromFile行を取得する方法について何を知っている必要はありません。呼び出されたときには、ラインを望んでいるだけのこと。

Main 今例えばピュアDIを使用するようにリファクタリングすることができます

static void Main() {
    IReadLines reader = new ReadLinesImplementation("path-to-file");
    IParsePersonInformationFromLine parser = new ParsePersonInformationFromLine(); 
    PersonReaderFromFile personReader = new PersonReaderFromFile(reader, parser);
    Person p = personReader.GetNext();  //return a Person parsed from file line or NULL at EOF
}

適用することができるが、これだけしっかりと実装の問題に連結されるコードの抽象化されるべき特定の実装の詳細の単純化した例であることを意味するさらなるリファクタリングがあります。

おすすめ

転載: http://43.154.161.224:23101/article/api/json?id=369765&siteId=1