奇怪的结构行为

本文关键字:结构 | 更新日期: 2023-09-27 18:14:49

我编写了一小段代码片段来演示这个问题。问题是,当我用Layout.Explicit状态声明一个结构体时,它根据另一个值将一个未定义的值赋给该结构体的字段。此问题仅在使用Layout.Explicit状态时发生。没有代码很难解释,所以这里有一个简短的示例。

using System.Runtime.InteropServices;
namespace ConsoleStruct
{
    class Program
    {
        [StructLayout(LayoutKind.Explicit)]
        struct TestStruct
        {
            [FieldOffset(0)]
            public double dbl;
            [FieldOffset(0)]
            public ulong uu;
        }
        public static void SimpleMethod()
        {
            TestStruct st;
            st.uu = 0;
            st.dbl = 5000.0;
            Console.WriteLine(st.uu.ToString()); // ==> uu becomes 4662219572839972864 
                                                 //instead of 0 :(
                                                 // it looks like the value of uu is dependent on the 
                                                 //value assigned to dbl
            Console.ReadLine();
        }
        static void Main(string[] args)
        {
            SimpleMethod();
        }
    }
}
谁能给我解释一下为什么会发生这种事?使用VS 2013。谢谢。

奇怪的结构行为

看起来uu的值依赖于分配给dbl的值

是的。因为你给了它们相同的偏移量,它们在内存中占据了相同的位置(在结构体中)。

[FieldOffset(...)]让您手动布局字段,您可以使它们重叠。一些非托管api需要这样做。

请注意,当您尝试与引用字段(如字符串)重叠时,您将获得运行时异常。只有在只使用值类型时才能维护内存安全。