5

我正在定义要通过不同设备和不同编程语言之间的通信通道接收和发送的结构。为此,我使用StructLayoutAttribute明确定义它们在内存中的布局(顺序,pack=1 - 以防万一)。

从文档中,我知道它在结构仅包含字段时有效。它似乎也适用于“简单”属性(使用空 get; set;)。但是我不知道是否总是这样。

所以我关于 StructLayoutAttribute 对属性的影响的问题分为两个:

  1. 简单的属性(同样是空的 get;set;)的行为是否与字段相同?
  2. 其他属性如何表现,例如,他们获得的属性是对其他属性的计算?它们是否被忽略(因为我没有看到它们背后的实际数据项)?他们有记忆吗?
4

3 回答 3

3

属性没有存储空间。StructLayoutAttribute完全不影响他们。

自动属性访问一个生成的支持字段,该字段受制于StructLayoutAttribute(因为所有字段都受制于此属性)。然而,这些字段的顺序没有定义。

由于仅计算值的 get-properties 没有存储空间,因此它们不会被封送。

于 2015-02-12T21:50:07.417 回答
2

根据文档和我的测试 FieldOffsetAttribute 不能应用于属性。这就留下了 LayoutKind.Sequential 的问题。根据这篇文章,属性字段出现在最后。如果您关心布局,基本上不要使用自动属性。展开它们并注释字段。计算的属性不会出现在结构的内存布局中。

于 2015-02-13T17:24:06.113 回答
1

自动属性 ​​( {get; set;}) 有一个自动创建的公开不可访问的支持字段。实际上,如果您使用反射查看具有 auto 属性的类的字段,您可以看到该属性有一个私有字段。下面的代码打印<Bar>k__BackingField了一个奇怪的字段名,但仍然是一个字段名!

我不能说我已经尝试StructLayoutAttribute过房产。如果它有效,它肯定只是将相同的逻辑应用于支持字段。

using System;
using System.Reflection;

namespace ConsoleApplication10
{
    class Program
    {
        static void Main(string[] args)
        {
            var fields = typeof(Foo).GetFields(BindingFlags.NonPublic | BindingFlags.Instance);
            Console.WriteLine(fields[0].Name);
        }
    }

    class Foo
    {
        public int Bar { get; set; }
    }
}
于 2015-02-12T21:50:28.523 回答