C #에서 문을 사용하여 중첩 = new DirectoryInfo(Environment.CurrentDirectory + “\\TestArea\\”); FileInfo[]

프로젝트를 진행 중입니다. 두 파일의 내용을 비교하여 서로 정확히 일치하는지 확인해야합니다.

많은 오류 검사 및 유효성 검사 전에 첫 번째 초안은 다음과 같습니다.

  DirectoryInfo di = new DirectoryInfo(Environment.CurrentDirectory + "\\TestArea\\");
  FileInfo[] files = di.GetFiles(filename + ".*");

  FileInfo outputFile = files.Where(f => f.Extension == ".out").Single<FileInfo>();
  FileInfo expectedFile = files.Where(f => f.Extension == ".exp").Single <FileInfo>();

  using (StreamReader outFile = new StreamReader(outputFile.OpenRead()))
  {
    using (StreamReader expFile = new StreamReader(expectedFile.OpenRead()))
    {
      while (!(outFile.EndOfStream || expFile.EndOfStream))
      {
        if (outFile.ReadLine() != expFile.ReadLine())
        {
          return false;
        }
      }
      return (outFile.EndOfStream && expFile.EndOfStream);
    }
  }

중첩 된 using문장 을 갖는 것은 약간 이상하게 보입니다 .

더 좋은 방법이 있습니까?



답변

이를 위해 선호되는 방법은 다음 과 같이 {마지막 using문장 뒤에 여는 중괄호 만 넣는 것입니다.

using (StreamReader outFile = new StreamReader(outputFile.OpenRead()))
using (StreamReader expFile = new StreamReader(expectedFile.OpenRead()))
{
    ///...
}


답변

객체의 유형같은 경우 다음을 수행 할 수 있습니다.

using (StreamReader outFile = new StreamReader(outputFile.OpenRead()),
                    expFile = new StreamReader(expectedFile.OpenRead()))
{
    // ...
}


답변

IDisposable유형이 동일한 경우 다음을 수행 할 수 있습니다.

 using (StreamReader outFile = new StreamReader(outputFile.OpenRead()),
     expFile = new StreamReader(expectedFile.OpenRead()) {
     // ...
 }

MSDN 페이지 using의이 언어 기능에 대한 설명서가 있습니다.

IDisposable유형이 같은지 여부에 관계없이 다음을 수행 할 수 있습니다 .

using (StreamReader outFile = new StreamReader(outputFile.OpenRead()))
using (StreamWriter anotherFile = new StreamReader(anotherFile.OpenRead()))
{
     // ...
}


답변

using 블록 전에 using 블록에 대한 변수를 선언하는 것이 마음에 들지 않으면 모두 동일한 using 문으로 선언 할 수 있습니다.

    Test t;
    Blah u;
    using (IDisposable x = (t = new Test()), y = (u = new Blah())) {
        // whatever...
    }

그렇게하면 x와 y는 using 블록에 사용할 IDisposable 유형의 자리 표시 자 변수 일 뿐이며 코드 내에서 t와 u를 사용합니다. 내가 언급 할 줄 알았는데


답변

파일을 효율적으로 비교하려면 StreamReader를 전혀 사용하지 말고 사용하지 않아도됩니다. 낮은 수준의 스트림 읽기를 사용하여 비교할 데이터 버퍼를 가져올 수 있습니다.

또한 파일 크기와 같은 것을 먼저 비교하여 다른 파일을 빠르게 감지하여 모든 데이터를 읽을 필요가 없도록 할 수 있습니다.


답변

using 문은 IDisposable 인터페이스에서 작동하므로 다른 옵션은 IDisposable을 구현하고 일반적으로 using 문에 넣을 모든 IDisposable 객체에 대한 참조를 갖는 복합 클래스 유형을 만드는 것입니다. 이것의 단점은 변수를 먼저 선언하고 범위 밖에서 변수를 선언해야 다른 제안 중 필요한 것보다 많은 코드 줄이 필요한 using 블록 내에서 변수가 유용하다는 것입니다.

Connection c = new ...;
Transaction t = new ...;

using (new DisposableCollection(c, t))
{
   ...
}

이 경우 DisposableCollection의 생성자는 params 배열이므로 원하는만큼 입력 할 수 있습니다.


답변

당신은 또한 말할 수 있습니다 :

using (StreamReader outFile = new StreamReader(outputFile.OpenRead()))
using (StreamReader expFile = new StreamReader(expectedFile.OpenRead()))
{
   ...
}

그러나 어떤 사람들은 그것을 읽기가 어렵다는 것을 알게 될 것입니다. BTW는 문제를 최적화하기 위해 한 줄씩 이동하기 전에 파일 크기가 같은 크기인지 먼저 확인하지 않는 이유는 무엇입니까?