【问题标题】:Possible to store references to objects in list?可以在列表中存储对对象的引用吗?
【发布时间】:2012-11-02 12:18:36
【问题描述】:

我希望能够在不直接引用它们的情况下为列表对象赋值:

伪例子:

List<int> intList = new List<int> { 0 };
???? intPointer = ref intlist[0];

*intPointer = 1;  // I know * isn't possible here, but it is what I'd like to do

Console.WriteLine(intList[0]);

它会输出1

我认为这是不可能的,但我只是想确保我没有遗漏任何东西。

另外,我不是在寻找使用 unsafe 的示例,我很好奇这在托管代码中是否可行。

【问题讨论】:

  • “不直接引用它们”是什么意思?
  • 我想通过另一个变量知道list[0]里面有什么
  • 所以您想要引用单个数组元素?请参阅 C# 中的 reference vs value types。 C# 中的引用类型(任何class 的实例)总是通过引用传递(类似于 在 C 中传递指针)。另一方面,值类型在传递时总是复制。因此,对于值类型(如 intfloatstruct 和类似的),这是不可能的。但是,如果您将它们设为引用类型的属性,那么您将能够获得引用。

标签: c#


【解决方案1】:

C# 没有“ref locals”的概念 (the CLR does though)。因此,您需要将值包装在可以变异的引用类型中。例如,

public class Ref<T> where T : struct
{
    public T Value {get; set;}
}

List<Ref<int>> intRefList = new List<Ref<int>>();
var myIntRef = new Ref<int> { Value = 1 };
intRefList.Add(myIntRef);

Console.WriteLine(myIntRef.Value);//1

Console.WriteLine(intRefList[0].Value);//1

myIntRef.Value = 2;

Console.WriteLine(intRefList[0].Value);//2

编辑:C# 7.0 添加了ref locals,但它们仍然不能以这种方式使用,因为您不能将 ref locals 放入数组或列表中。

【讨论】:

    【解决方案2】:

    不,这在 C# 中是不可能的。

    C# 不支持对局部变量的引用,其中包括对本地容器元素的引用。

    在 C# 中获得真正引用的唯一方法(即,不是引用类型的实例,而是对另一个变量的实际引用)是通过 refout参数关键字。这些关键字不能与任何类型的索引值或属性一起使用,其中包括List&lt;&gt; 中的元素。您也无法直接控制这些引用:编译器在幕后为您执行取消引用。

    有趣的是,CLR确实支持这种引用;如果你将 CIL 反编译成 C#,你有时会看到像 int&amp; 这样的类型是对 int 的引用。 C# 故意不允许您在代码中直接使用这些类型。

    【讨论】:

      【解决方案3】:

      当使用 value type (例如 int)时,您的要求是不可能的。您将需要额外的间接级别;例如,你可以包装你的整数。

      请参阅 Mutable wrapper of value types to pass into iterators 了解相关示例。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-03-07
        • 1970-01-01
        • 2010-12-29
        • 1970-01-01
        • 2022-09-24
        • 1970-01-01
        相关资源
        最近更新 更多