1

插入较小的图像可以正常工作。但是,当图像文件大于大约 2MB 时,我会得到一个OutOfMemoryException.

我尝试了SqlCeUpdatableRecord一个参数化的SqlCeCommand. 使用SqlCeCommand,在 处引发异常ExecuteNonQuery()

使用SqlCeUpdatableRecord时,会在 处引发异常SqlCeUpdatableRecord.SetBytes()

我尝试增加缓冲区大小和临时文件大小,但似乎没有效果。我已经调试过了GetTotalMemory,似乎有很多可用的资源。

任何提示将不胜感激。

SQL Server CE 数据库与主 SQL Server 数据库同步,将图像作为单独的文件处理会引入大量其他问题。该解决方案多年来一直运行良好,因为大多数 WM 手持设备只能以 5MP 或更低的速度捕获图像。但是,支持 8MP 图像的较新型号会导致问题。

这是实现的简化版本SqlCeUpdateblRecord

System.Data.SqlServerCe.SqlCeUpdatableRecord newRecord = base.CreateRecord();
newRecord["ImageId"] = ImageId;
newRecord["ImageType"] = ImageType;
//64kb buffer (Have tested with different buffer sizes (up to 8MB)
newRecord.SetBytesFromFile("ImageFull", ImageFullFileName, 65536);
newRecord["ImageThumb"] = ImageThumb;
newRecord["ImageDate"] = ImageDate;
base.Insert(newRecord); 

.....
public static void SetBytesFromFile(this SqlCeUpdatableRecord obj, string name, string filename, int buffersize)
{
    int _column = obj.GetOrdinal(name);
    byte[] buffer = new byte[buffersize];            
    int bytesread;
    long offset = 0;

    using (FileStream fs = new FileStream(filename,FileMode.Open))
    {
        bytesread = fs.Read(buffer, 0, buffersize);

        while (bytesread > 0)
        {
            //This will raise OutOfMemoryException for imagefiles larger than appx. 2mb, regardless of buffersize      
            obj.SetBytes(_column, offset, buffer, 0, bytesread);                    
            offset = offset + (long)bytesread;
            bytesread = fs.Read(buffer, 0, buffersize);           
        }
    }
}

这是参数化查询的简化版本:

using (var cmdInsert = new SqlCeCommand("INSERT INTO [Image_CF] ( [ImageId], [ImageType], [ImageFull], [ImageThumb], [ImageDate]) VALUES " +
                                                   " ( @ImageId, @ImageType, @ImageFull, @ImageThumb, @ImageDate)"))
{
    cmdInsert.Connection = Database.IrisPdaConnection;

    cmdInsert.Parameters.Add("@ImageId", System.Data.SqlDbType.Int).Value = ImageId;
    cmdInsert.Parameters.Add("@ImageType", System.Data.SqlDbType.NVarChar).Value = ImageType;
    cmdInsert.Parameters.Add("@ImageFull", System.Data.SqlDbType.Image).Value = GetFileAsBytes(ImageFullFileName);
    cmdInsert.Parameters.Add("@ImageThumb", System.Data.SqlDbType.Image).Value = ImageThumb;
    cmdInsert.Parameters.Add("@ImageDate", System.Data.SqlDbType.NVarChar).Value = ImageDate;

    // OutOfMemoryException for images larger than appx. 2MB
    cmdInsert.ExecuteNonQuery();
}

public byte[] GetFileAsBytes(string filename)
{
   FileStream fs;
   byte[] result;

   using (fs = new FileStream(filename, FileMode.Open, FileAccess.Read))
   {
        // a byte array to read the image
        result = new byte[fs.Length];     
        fs.Read(result, 0, System.Convert.ToInt32(fs.Length));  
   }

   return result; 
}
4

0 回答 0