2010-01-29 36 views
4

我對將圖像保存到數據庫的這種東西很陌生,甚至當我認爲這是非常直截了當的時候,事實並非如此。我想要做的是從同一臺計算機以任何格式讀取圖像文件,並將其顯示在圖片框中,然後將圖像轉換爲字節以將其保存在數據庫中。到目前爲止,我可以在圖片框中顯示圖像,但我無法將圖像轉換爲字節。這是我的代碼:無法將圖像轉換爲字節[] C#

private void DisplayImage() 
    { 
     if (openFileDialog.ShowDialog(this) == DialogResult.OK) 
     { 
      try 
      { 
       Stream file; 
       if ((archivo = openFileDialog.OpenFile()) != null) 
       { 
        using (file) 
        { 
         pictureBox.Image = Image.FromStream(file); 
        } 
       } 
      } 
      catch (Exception ex) 
      { 
       ... 
      } 
     } 
    } 

這是一個簡單的方法,只是在圖片框中顯示圖像。真正的問題是用下面的方法:

public static byte[] ConvertImageToBytes(Image image) 
    { 
     if (image != null) 
     { 
      MemoryStream ms = new MemoryStream(); 
      using (ms) 
      { 
       image.Save(ms, ImageFormat.Bmp); 
       byte[] bytes = ms.ToArray(); 

       return bytes; 
      } 
     } 
     else 
     { 
      return null; 
     } 
    } 

當它試圖將圖像保存到內存流,我得到的錯誤:

System.Runtime.InteropServices.ExternalException: A generic error occurred in GDI+. 

上發生了什麼任何想法?

+0

是錯誤總是發生,或者只是偶爾,或者使用時間長的申請後? – Chris 2010-01-29 05:16:28

+0

你永遠不會在第一個方法中分配'文件'變量......我認爲這只是真實代碼的一個提取?否則,編譯器會抱怨在分配之前使用'文件'變量? – 2010-01-29 06:40:31

回答

1

這可能是愚蠢的回答我自己的問題,但我只是發現,如果我想將圖像對象轉換爲字節,我必須保持原始流打開。我在另一個我不太記得的頁面中看到了這個問題,並且我通過將流打開並且是真的來測試它。所以格式不是問題。但我會接受你們所有人的建議並將圖像存儲在一個單獨的目錄中。謝謝你們的幫助!

1

這種特殊的異常通常意味着您正試圖將圖像保存爲錯誤的格式。在你的代碼中,你指定ImageFormat.Bmp - 它實際上是一個位圖圖像,還是你可能從JPEG或PNG加載它?試圖保存爲您加載的格式不同於ExternalException將會失敗,如documentation中所述。順便說一句,我不建議將圖像存儲在數據庫中,我相信這裏的大多數人會同意。數據庫可能能夠處理這個任務,但它們並未針對它進行優化,最終會損害數據庫和應用程序的性能。除非您使用SQL Server 2008 FILESTREAM列,否則在文件系統上存儲圖像效率更高。

+0

+1 - 我懷疑是一樣的。圖像格式不匹配。 – Gishu 2010-01-29 05:03:58

3

您應該使用原始圖像的RawFormat屬性作爲Save方法的參數,而不是默認的位圖。這將避免圖像格式類型錯誤。例如:

image.Save(ms, image.RawFormat); 

    ms.Position = 0; 

    byte [] bytes=ms.ToArray(); 

我建議實際上保存圖像的文件系統並簡單地在數據庫中存儲的文件路徑(優選相對)。

數據庫中的BLOB(即圖像等)無法編入索引,通常存儲在輔助的較慢訪問數據庫區域,並且會很快將數據庫的大小(比較慢的備份等)吹掉。

2

廣東話您只需閱讀文件,然後使用File類加載到一個byte []:

byte[] imgData = System.IO.File.ReadAllBytes(@"C:\My Pic\Myfile.jpg"); 

你可以選擇從打開的對話框中的圖像路徑。

0

這樣做的問題是該流必須在映像的生命週期中打開,否則將失敗。爲我工作

一種解決方案是隻是爲了創造這樣的圖像的副本:

using (var ms = new MemoryStream(bytes)) 
{ 
    _image = new Bitmap(Image.FromStream(ms)); 
}