微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

将局部变量分配给只读字段的引用C# 等效于“const &”

如何解决将局部变量分配给只读字段的引用C# 等效于“const &”

我有一个 struct 存储在 readonly 字段中,嵌套在几个级别的对象中(全部在我无法控制的代码中),我正在一个函数中访问这些对象。例如:

struct Surprise { public readonly int a,b,c; }
struct Gizmo { public readonly Surprise surprise; }
struct Bobble { public readonly Gizmo gizmo; }
struct Thing { public readonly Bobble bobble; }
class Gift { public readonly Thing thing; }

void Function (Gift gift) {
    int contrived = gift.thing.bobble.gizmo.surprise.a +
                    gift.thing.bobble.gizmo.surprise.b + 
                    gift.thing.bobble.gizmo.surprise.c;
}

纯粹是为了避免每次使用时都必须输入 gift.thing.bobble.gizmo.surprise,我想将其分配给具有较短名称的局部变量。但是,我也不需要复制结构体,所以我想避免这种情况:

void Function (Gift gift) {
    
    { // (A) this is what i'm trying to not type out:
        int contrived = gift.thing.bobble.gizmo.surprise.a + 
                        gift.thing.bobble.gizmo.surprise.b +
                        gift.thing.bobble.gizmo.surprise.c;
    }
    
    { // (B) i can do this,but i don't *need* to copy,so i'd like to avoid:
        Surprise s = gift.thing.bobble.gizmo.surprise;
        int contrived = s.a * s.b + s.c;
    }
    
    { // (C) what i *want* to do is something like this:
        ref Surprise s = ref gift.thing.bobble.gizmo.surprise;
        int contrived = s.a * s.b + s.c;
    }
    
}

但是,似乎不允许使用变体 (C),因此无法编译:

CS0192 A readonly field cannot be used as a ref or out value
  (except in a constructor)

我的问题是:有没有办法创建一个局部变量来引用只读值类型字段并且不复制它(或其他一些方法来节省一些输入)?

我是 C# 的新手,来自 C++。如果您熟悉 C++,我基本上是在寻找等效的:

const Surprise &s = gift->thing.bobble.gizmo.surprise;

另外:它甚至会有所作为,还是编译器足够聪明,不会在上面的 (B) 中创建副本?


顺便说一下,经过一番挣扎,我确实想出了这个噩梦:

delegate void Hack (in Surprise s);

void Function (Gift gift) {
    ((Hack)((in Surprise s) => {
        int contrived = s.a + s.b + s.c;
        ...;
    }))(gift.thing.bobble.gizmo.surprise);
}

不过,出于希望显而易见的原因,我对此选项不感兴趣。此外,我实际上不确定这是否甚至避免了副本。

解决方法

扩展方法怎么样。

public static class GiftExtension
{
    public static int Sum(this Gift gift)
    {
        int contrived = gift.thing.bobble.gizmo.surprise.a +
                            gift.thing.bobble.gizmo.surprise.b +
                            gift.thing.bobble.gizmo.surprise.c;
        return contrived;
    }
    public static int Sum(this Surprise surprise)
    {
        int contrived = surprise.a +
                            surprise.b +
                            surprise.c;
        return contrived;
    }
}

然后在你的方法中,你可以有

void Function(Gift gift)
    {
        {
            //(A)  was trying to use a pointer to access the memory location,couldn't get it to work!
            //unsafe
            //{
            //    Surprise* ps = &(gift.thing.bobble.gizmo.surprise);
            //}
        }
        //(B)
        {
            int contrived = gift.Sum();
        }
        {
            int contrived = gift.thing.bobble.gizmo.surprise.Sum();
        }
    }
,

创建一个 readonly 属性来访问您想要的值。

public struct Surprise
{
    get
    {
        return gift.thing.bobble.gizmo.surprise;
    }
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。