2011-05-27 75 views
0

我有這樣的一段代碼,並生成一個錯誤:編組結構

[StructLayout(LayoutKind.Sequential, Pack = 1)] 
    public struct MyItem 
    { 
     [MarshalAs(UnmanagedType.LPWStr)] 
     public string Name; 
     public int ID; 
     public double ID1; 

    } 

    private void button1_Click(object sender, RoutedEventArgs e) 
    { 

     MyItem[] items = new MyItem[6]; 
     items[0].Name = "JFK"; 
     items[0].ID = 35; 
     items[1].Name = "LBJ"; 
     items[1].ID = 36; 
     items[2].Name = "Tricky Dicky"; 
     items[2].ID = 37; 
     items[3].Name = "Gerald Ford"; 
     items[3].ID = 38; 
     items[4].Name = "Jimmy Carter"; 
     items[4].ID = 39; 
     items[5].Name = "Ronald Reagan"; 
     items[5].ID = 40; 

     IntPtr itemsPtr = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(MyItem)) * 
      items.Length); 
     try 
     { 
      IntPtr item = new IntPtr(itemsPtr.ToInt32()); 
      for (int i = 0; i < items.Length; i++) 
      { 
       Marshal.StructureToPtr(items[i], item, true); 
       item = new IntPtr(item.ToInt32() + Marshal.SizeOf(typeof(MyItem))); 
      }   
     } 
     finally 
     { 
      Marshal.FreeHGlobal(itemsPtr); 
     } 

當我運行這段代碼,我得到write protection error in Marshal.StructureToPtr(items[i], item, true);

這是什麼問題,如何解決這個問題?

+0

不能你擡頭38 39 40等! – 2011-05-27 21:23:49

+0

@David:你是什麼意思?你能解釋一下:) – mans 2011-05-27 21:26:24

+0

你在64位機器上運行嗎? – 2011-05-27 21:28:22

回答

4

您應該將false傳遞給參數StructureToPtr()fDeleteOld

通過傳遞true您要求編組人員刪除item的內容。由於您是第一次填寫此內容,因此內存訪問失敗,因爲內存尚未生效。

的文檔狀態:

StructureToPtr copies the contents of structure to the pre-allocated block of memory that the ptr parameter points to. If the fDeleteOld parameter is true, the pre-allocated buffer is deleted with the appropriate deletion method on the embedded pointer, but the buffer must contain valid data.

的重點是我的。

順便說一句,我認爲循環代碼看起來整潔是這樣的:

Int32 addr = itemsPtr.ToInt32(); 
for (int i = 0; i < items.Length; i++) 
{ 
    Marshal.StructureToPtr(items[i], new IntPtr(addr), false); 
    addr += Marshal.SizeOf(typeof(MyItem)); 
} 
+0

@user這個代碼最初來自我的一個早先的問題,錯誤的設置'fDeleteOld'實際上是我的錯誤。我道歉! – 2011-05-27 21:55:07

+0

感謝您的幫助。我在哪裏可以閱讀更多關於這面旗幟如果設置爲false,爲什麼會產生內存泄漏? – mans 2011-05-27 22:16:27

+0

在msdn的文檔中閱讀它。這裏沒有泄漏,因爲非託管內存不包含任何泄漏。 – 2011-05-27 22:21:12