2013-05-27 18 views
0

我正在建立一些代码,通过FtpWebRequest下载图片。当我收集对DownloadFile流的响应时,我能够将内存中的图像返回到调用函数的唯一方法是使用MyResponseStream.CopyTo(MyMemoryStream),然后使用Return MyMemoryStream。这有效,但我不明白为什么我需要在内存中创建一个图像的两个副本(可能会非常大)。当我试图直接返回MyResponseStream时,代码只是挂在空间的某个地方,我不得不停止调试器。为什么我必须将FTP流复制到另一个变量才能将其返回给调用方法?

为什么我不能这样做?:Return MyResponseStream在下面的代码中?

Imports System.IO 
Imports System.Net 

Public Function GetJpgImage(ByVal ImageID As Integer) 
    'returns image file from server in a memoryStream 
    'code from: http://www.dreamincode.net/forums/topic/77912-ftp-download-delete/ 

    'build requested file string 
    Dim MyRequestedFile As String 
    MyRequestedFile = ImageID.ToString & ".jpg" 

    'create FTP request 
    Dim ftpRequest As FtpWebRequest = DirectCast(WebRequest.Create("ftp://mysite.com/www/downloads/" & MyRequestedFile), FtpWebRequest) 
    ftpRequest.Credentials = New NetworkCredential("mySpecialUser", "superSecretPwd") 
    ftpRequest.UseBinary = True 
    ftpRequest.KeepAlive = False 'No Zombies 

    'check if file exists (sigh... do it later) 

    'select download method 
    ftpRequest.Method = WebRequestMethods.Ftp.DownloadFile 

    'setup for response 
    Dim MyMemoryStream As New MemoryStream 
    Dim FTPResponse As FtpWebResponse = DirectCast(ftpRequest.GetResponse, FtpWebResponse) 

    'send request and return memoryStream 
    Using MyResponseStream As IO.Stream = FTPResponse.GetResponseStream 
     'copy to memory stream so we can close the FTP connection 
     MyResponseStream.CopyTo(MyMemoryStream) '<== Why God? Why? 
     'close FTP stream 
     MyResponseStream.Close() 
     'gimme my data! 
     Return MyMemoryStream 
    End Using 
End Function 

它没有任何与MyResponseStreamUsing声明(我试过)之中。 VS 2012,Win8。

回答

1

你为什么不具备的功能声明如下:

Public Function GetJpgImage(ByVal ImageID As Integer) as MemoryStream 

,如果你正在返回:

Return MyMemoryStream 

编辑:尝试改变return语句从使用的,只是为了测试。 如果您在使用语句 中包含您的退货并不重要,但只是为了确保。因为你所遇到的行为是不正常的,以及

Using MyResponseStream As IO.Stream = FTPResponse.GetResponseStream 
    'copy to memory stream so we can close the FTP connection 
    MyResponseStream.CopyTo(MyMemoryStream) '<== Why God? Why? 
    'close FTP stream 
    MyResponseStream.Close() 
    'gimme my data! 

End Using 

Return MyMemoryStream 

EDIT2:。如果你不想使用复制到,请尝试使用传统的方式来读取流进的MemoryStream:

MemoryStream memStream; 
using (Stream response = request.GetResponseStream()) { 
    memStream = new MemoryStream(); 

    byte[] buffer = new byte[1024]; 
    int byteCount; 
    do { 
     byteCount = stream.Read(buffer, 0, buffer.Length); 
     memStream.Write(buffer, 0, byteCount); 
    } while (byteCount > 0); 
} 
+0

其实我有它宣称的方式最初,它似乎并没有把这个差异题。最后我会再补充一遍。可以肯定的是,我在函数declare中使用'作为MemoryStream'和'IO.Stream'进行测试。当我尝试返回'MyResponseStream'时仍然挂起。 – turbonate

+0

更新了我的答案。只是试图帮助,因为它真的很奇怪 –

+0

欣赏的想法,让我在这里添加一些澄清。在发布的问题中的代码作品,但我想弄清楚为什么在世界上我不得不使用'CopyTo()'方法来返回流。我尝试使用DIM语句而不是使用结构,仍然有相同的结果,所以我不认为'使用'方法是问题。虽然我没有直接尝试这个想法,但我已经有效地测试了这个变体,它的工作原理与将它保留在内部一样。并且基于同样的想法,我无法将'MyResponseStream'返回到using块之外,因为它已经被处理掉了。 – turbonate

相关问题