문제

PDF 파일 조작을 수행하는 타사 구성 요소가 있습니다. 작업을 수행해야 할 때마다 문서 저장소 (데이터베이스, SharePoint, 파일 시스템 등)에서 PDF 문서를 검색합니다. 일을 조금 일관성있게 만들려면 PDF 문서를 byte[].

이 타사 구성 요소는 a MemoryStream[] (MemoryStream 배열) 사용해야하는 주요 방법 중 하나의 매개 변수로.

응용 프로그램 내의 여러 영역 에이 기능을 사용할 수 있도록이 기능을 자체 구성 요소로 래핑하려고합니다. 나는 본질적으로 다음을 생각해 냈습니다.

public class PdfDocumentManipulator : IDisposable
{
   List<MemoryStream> pdfDocumentStreams = new List<MemoryStream>();

   public void AddFileToManipulate(byte[] pdfDocument)
   {
      using (MemoryStream stream = new MemoryStream(pdfDocument))
      {
         pdfDocumentStreams.Add(stream);
      }
   }

   public byte[] ManipulatePdfDocuments()
   {
      byte[] outputBytes = null;

      using (MemoryStream outputStream = new MemoryStream())
      {
           ThirdPartyComponent component = new ThirdPartyComponent();
           component.Manipuate(this.pdfDocumentStreams.ToArray(), outputStream);

           //move to begining
           outputStream.Seek(0, SeekOrigin.Begin);

           //convert the memory stream to a byte array
           outputBytes = outputStream.ToArray();
      }

      return outputBytes;
   }

   #region IDisposable Members
   public void Dispose()
   {
       for (int i = this.pdfDocumentStreams.Count - 1; i >= 0; i--)
       {
          MemoryStream stream = this.pdfDocumentStreams[i];
          this.pdfDocumentStreams.RemoveAt(i);
          stream.Dispose();
       }
   }
   #endregion
}

내 "래퍼"에 대한 호출 코드는 다음과 같습니다.

    byte[] manipulatedResult = null;
    using (PdfDocumentManipulator manipulator = new PdfDocumentManipulator())
    {
        manipulator.AddFileToManipulate(file1bytes);
        manipulator.AddFileToManipulate(file2bytes);
        manipulatedResult = manipulator.Manipulate();
    }

위의 몇 가지 질문 :

  1. 입니다 using 절의 조항 AddFileToManipulate() 방법 중복 및 불필요?
  2. 내 객체에서 괜찮은 것을 정리하고 있습니까? Dispose() 방법?
  3. 이것은 "허용 가능한"사용입니다 MemoryStream? 한 번에 메모리에서 많은 파일을 기대하지 않습니다 ... 아마도 1-10 총 PDF 페이지, 각 페이지는 약 200kb입니다. ASP.NET 사이트를 지원하는 서버에서 실행되도록 설계된 앱.
  4. 의견/제안이 있습니까?

코드 검토에 감사드립니다 :)

도움이 되었습니까?

해결책

  1. addfiletomanipulate () 메소드의 사용 절은 중복되고 불필요합니까?

더 나쁜 것은 파괴적입니다. 기본적으로 메모리 스트림이 추가되기 전에 닫습니다. 자세한 내용은 다른 답변을 참조하십시오. 그러나 기본적으로는 끝에 폐기하지만 다른 시간은 아닙니다. 객체와 함께 사용하면 메소드를 통해 객체가 다른 객체에 "전달"되더라도 블록 끝에서 처분이 발생합니다.

  1. 내 객체의 dispose () 메소드에서 괜찮은 것을 정리하고 있습니까?

그렇습니다.하지만 당신은 필요한 것보다 인생을 더 어렵게 만들고 있습니다. 이 시도:

foreach (var stream in this.pdfDocumentStreams)
{
    stream.Dispose();
}
this.pdfDocumentStreams.Clear();

이것은 마찬가지로 작동하며 훨씬 간단합니다. 객체를 처리한다고해서 삭제하지는 않습니다. 단지 내부의 관리되지 않은 리소스를 자유롭게 알려줍니다. 이런 식으로 객체에 처분하는 것은 괜찮습니다. 컬렉션에서 객체가 수집되지 않은 상태로 유지됩니다. 이 작업을 수행 한 다음 한 번의 샷으로 목록을 지울 수 있습니다.

  1. 이것은 메모리 스트림의 "허용 가능한"사용입니까? 한 번에 메모리에서 많은 파일을 기대하지 않습니다 ... 아마도 1-10 총 PDF 페이지, 각 페이지는 약 200kb입니다. ASP.NET 사이트를 지원하는 서버에서 실행되도록 설계된 앱.

이것은 당신의 상황에 달려 있습니다. 이러한 파일을 메모리에 사용하는 오버 헤드가 문제를 일으킬 지 여부를 결정할 수 있습니다. 그러나 이것은 상당히 무거운 웨이트 객체가 될 것이므로 조심스럽게 사용할 것입니다.

  1. 의견/제안이 있습니까?

최종화기를 구현하십시오. idisposable을 구현할 때마다 좋은 생각입니다. 또한 처분 구현을 표준 구현으로 재 작업하거나 클래스를 봉인 된 것으로 표시해야합니다. 이 작업을 수행 해야하는 방법에 대한 자세한 내용은 이 기사를 참조하십시오. 특히, 당신은 다음과 같은 방법을 선언해야합니다. protected virtual void Dispose(bool disposing) 귀하의 처분 방법과 파이널 라이저 모두 호출.

다른 팁

addfiletmanipulate가 나를 두려워합니다.

   public void AddFileToManipulate(byte[] pdfDocument)
   {
      using (MemoryStream stream = new MemoryStream(pdfDocument))
      {
         pdfDocumentStreams.Add(stream);
      }
   }

이 코드는 pdfdocumentstream 목록에 배치 스트림을 추가합니다. 대신 다음을 사용하여 스트림을 추가해야합니다.

   pdfDocumentStreams.Add(new MemoryStream(pdfDocument));

처분 방법에 폐기하십시오.

또한 누군가가 최상위 객체를 처분하는 것을 잊어 버린 경우에 물건이 배치 될 수 있도록 최종화기를 구현하는 것을 살펴 봐야합니다.

그것은 당신이 사용하는 것이 무엇을하는지 오해하는 것처럼 보입니다.

교체하는 것은 구문 설탕 일뿐입니다

MemoryStream ms;
try
{
ms = new MemoryStream();
}
finally
{
ms.Dispose();
}

AddFileTomanipulate의 사용량은 중복됩니다. PDFDocumentManipulator의 생성자에 MemoryStreams 목록을 설정 한 다음 모든 MemoryStream에 PDFDocumentManipulator의 Dispose Method Call Dispocation을 설정했습니다.

참고 사항. 이것은 실제로 확장 방법을 요구하는 것처럼 보입니다.

public static void DisposeAll<T>(this IEnumerable<T> enumerable)
  where T : IDisposable {
  foreach ( var cur in enumerable ) { 
    cur.Dispose();
  }
}

이제 귀하의 처분 방법이됩니다

public void Dispose() { 
  pdfDocumentStreams.Reverse().DisposeAll();
  pdfDocumentStreams.Clear();
}

편집하다

확장 방법을 갖기 위해 3.5 프레임 워크가 필요하지 않습니다. 그들은 2.0을 대상으로하는 3.0 컴파일러에서 행복하게 작업 할 것입니다.

http://blogs.msdn.com/jaredpar/archive/2007/11/16/extension-methods-without-3-5-framework.aspx

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top