2014-11-29 2 views
-3

form1에는 하나의 파일 또는 여러 파일의 디렉토리에서 파일을 선택할 수있는 두 개의 버튼이 있습니다. 두 번째 단추는 선택한 디렉터리의 모든 파일을 가져 오기 위해 디렉터리에서 파일을 선택하는 것입니다.FileInfo []가 필요한 경우 어떻게 사용할 수 있습니까? 아니면 필요하면 문자열 []을 사용할 수 있습니까?

지금 내가 파일을 업로드하기 위해 사용하고 클래스가/내 FTP로 디렉토리를 다음

public static DirectoryInfo d; 
public static string[] files; 
private FileInfo[] dirflist; 

난 경우에 그것을 사용하고 있습니다 : 내가 한 클래스의 상단에 :

private void FtpProgress_DoWork(object sender, DoWorkEventArgs e) 
     { 
      try 
      { 
       dirflist = d.GetFiles(); 
       //if (dirflist.Length > 0) 
       //{ 
        foreach (string txf in files) 
        { 
         string fn = txf;//txf.Name; 
         BackgroundWorker bw = sender as BackgroundWorker; 
         f = e.Argument as FtpSettings; 
         string UploadPath = String.Format("{0}/{1}{2}", f.Host, f.TargetFolder == "" ? "" : f.TargetFolder + "/", Path.GetFileName(fn));//f.SourceFile)); 
         if (!UploadPath.ToLower().StartsWith("ftp://")) 
          UploadPath = "ftp://" + UploadPath; 
         FtpWebRequest request = (FtpWebRequest)WebRequest.Create(UploadPath); 
         request.UseBinary = true; 
         request.UsePassive = f.Passive; 
         request.Method = WebRequestMethods.Ftp.UploadFile; 
         request.Timeout = 300000; 
         request.Credentials = new NetworkCredential(f.Username, f.Password); 
         long FileSize = new FileInfo(f.SourceFile).Length; 
         string FileSizeDescription = GetFileSize(FileSize); 
         int ChunkSize = 4096, NumRetries = 0, MaxRetries = 50; 
         long SentBytes = 0; 
         byte[] Buffer = new byte[ChunkSize]; 
         using (Stream requestStream = request.GetRequestStream()) 
         { 
          using (FileStream fs = File.Open(f.SourceFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite)) 
          { 
           int BytesRead = fs.Read(Buffer, 0, ChunkSize); 
           while (BytesRead > 0) 
           { 
            try 
            { 
             if (bw.CancellationPending) 
              return; 

             requestStream.Write(Buffer, 0, BytesRead); 

             SentBytes += BytesRead; 

             string SummaryText = String.Format("Transferred {0}/{1}", GetFileSize(SentBytes), FileSizeDescription); 
             bw.ReportProgress((int)(((decimal)SentBytes/(decimal)FileSize) * 100), SummaryText); 
            } 
            catch (Exception ex) 
            { 
             Debug.WriteLine("Exception: " + ex.ToString()); 
             if (NumRetries++ < MaxRetries) 
             { 
              fs.Position -= BytesRead; 
             } 
             else 
             { 
              throw new Exception(String.Format("Error occurred during upload, too many retries. \n{0}", ex.ToString())); 
             } 
            } 
            BytesRead = fs.Read(Buffer, 0, ChunkSize); 
           } 
          } 
         } 
         using (FtpWebResponse response = (FtpWebResponse)request.GetResponse()) 
          System.Diagnostics.Debug.WriteLine(String.Format("Upload File Complete, status {0}", response.StatusDescription)); 
        } 
       //} 
      } 
      catch (WebException ex) 
      { 
       switch (ex.Status) 
       { 
        case WebExceptionStatus.NameResolutionFailure: 
         ConnectionError = "Error: Please check the ftp address"; 
         break; 
        case WebExceptionStatus.Timeout: 
         ConnectionError = "Error: Timout Request"; 
         break; 
       } 
      } 
     } 

이제 문자열 [] 배열을 반복합니다. 여러 파일을 선택하고 있기 때문에.

그러나 내가 디렉토리를 선택할 수 있습니다. 그리고 난의 DirectoryInfo (D 변수) 등을 사용할 필요가있을에서는 FileInfo []

내가 사용하는 경우에서는 FileInfo [] 다음은 같다 :

dirflist = d.GetFiles(); 
       if (dirflist.Length > 0) 
       { 
        foreach (FileInfo txf in dirfilist) 
        { 
         string fn = txf.Name; 

하지만 난 싶지 않아 string [] 또는 FileInfo []에 대해서만 다시 모든 코드를 복사하십시오. foreach에서 foreach 또는 string []을 사용하여 FileInfo []를 사용할 수있는 무언가를 만들고 싶습니다.

그리고 때로는 여러 파일을 업로드하고 내부의 모든 파일을 포함하는 디렉토리를 업로드 할 때도 있습니다.

그래서 전체 코드를 복제하고 한 번 [] 문자열을 사용하고 FileInfo []를 사용하는 것이 더 좋을까요?

지금
private void CopyFile(string fn) 
{ 
    BackgroundWorker bw = sender as BackgroundWorker; 
    f = e.Argument as FtpSettings; 
    ... 
} 

당신이 원하는 처리 여부를 결정 : 나는 두 가지 방법을 의미 하나

+0

그냥'd.GetFileSystemInfos()'를 사용하십시오. 질문하기 전에 살펴 보았습니까? – BrokenGlass

+0

Ftp 전송 프로세스를 읽었습니다. 함수의 작업을 나눌 것입니다. While는 CancellationPending 처리를 포함하는 Function (파일 처리시 1을 반환하고 BW 취소시 0을 반환하고 Exception의 경우 -1을 반환 함)에서 파일 경로 당 파일 정보 (또는 FileInfo)를 가져 오는 작업을 이동합니다. 필요한 모든 멤버가있는 사용자 정의 클래스를 반환하는 함수 (버퍼링을 처리 할 함수에 해당 클래스 전달) - UI 용도로, 이러한 클래스에는 버퍼링, FTP 전송 및 발생 이벤트 처리 : chunck send, transfer complete , 취소 된... –

답변

1

은 어떻게 사용할 수 있습니까?

private void SomeMethod(args) 
{ 
    // ... 

    /* Here I need a specific String Value, or Array of String Values 
    but sometimes I got it from an array of File, 
    and sometimes from an array of FileInfo... */ 

    // Call a Function that always returns an array of String 
    files = GetMyFiles(args); 

    // resume the job using only files... 

    /* or replace the above that always manipulates an arrays of FileInfo-s 
    if you must use FileInfo-s */ 
} 

그럼 당신은 당신이 원하는 인수를 전달하여 함수의 GetMyFiles를 오버로드 할 수 있습니다.

string[] GetMyFiles(String DirectoryPath) 
// Returns an Array of String that contains all the Files in the Directory. 

string[] GetMyFiles(FileInfo MyFileInfo) 
// Returns an Array of String with just one File Path. 

string[] GetMyFiles() 
// Opens a MultiSelect OpenFileDialog, 
// then returns the selected Files Path in an Array (or empty Array) 

// ... 

다른 방법 : 다음 조건 검사로 사용하려고하고 어떤 부분을 결정, 여러 부분에서 코드를 슬라이스 ...

private void FtpProgress_DoWork(object sender, DoWorkEventArgs e) 
{ 
    // Do the maximum you can do here... 
    // ... 

    if ImGoingToUseStringArray 
    { 
     string[] files = .... 
     ResumeWithStringArray(files, sender, e); 
    } 
    else 
    { 
     FileInfo[] dirflist = .... 
     ResumeWithFileInfo(dirfList, sender, e); 
    } 
} 

private void ResumeWithStringArray(string[] files, object sender, DoWorkEventArgs e) 
{ 
    // ... 
    // you can also call another core Function from here 
    sendMyFile(args) 
} 

private void ResumeWithFileInfo(FileInfo[] dirflist, object sender, DoWorkEventArgs e) 
{ 
    // ... 
    // you can also call another core Function from here 
    sendMyFile(args) 
} 

어쨌든, 당신은 오른쪽 (I 가정 파일 전송에 필수) 파일 크기를 얻을 수에서는 FileInfo를 사용해야합니다? 그러나 FileInfo 을 만들 때마다 파일 (또는 동시에 여러 FileInfo-s를 사용하고 있습니까?) 처음부터 FileInfo의 목록/배열로 코드가 너무 복잡해 졌다고 생각하면 FileInfo의 각 인스턴스는 필요할 때 동적으로 (코드를 부분 분할)

귀하의 질문에 대한 답변은 귀하의 취향에 달려 있거나 논리를 실행하는 방식에 약간의 변경 만 필요합니다.

1

이 같은 별도의 방법으로 하나의 파일을 처리하는 모든 코드를 넣고 []에서는 FileInfo [] 하나의 문자열을 사용합니다 파일 목록 물건 또는 디렉토리 목록에 물건 및 통화 같은 새로운 방법

파일 목록 :

foreach (string txf in files) 
{ 
    this.CopyFile(txt); 
} 

디렉터리 목록 다음FileInfo[]를 필요한 경우 또는string[]를 필요한 경우

dirflist = d.GetFiles(); 
if (dirflist.Length > 0) 
{ 
    foreach (FileInfo txf in dirfilist) 
    { 
     this.CopyFile(txt.Name); 
    } 
} 
관련 문제