获取它的实例名

本文关键字:实例 获取 | 更新日期: 2023-09-27 18:08:24

这可能吗?

我正在尝试创建一组类来模拟许多不同类型的事物。这些东西的属性会随着时间的推移而改变,我希望我的代码易于维护,所以我想做如下的事情:

public class Cat
{
    public string CatName { get; set; }
    public Cat()
    {
        this.CatName = MAGICSTUFF.GetInstanceName(this);
     }
}

在其他地方,当我想要得到那些猫时,我希望能够说:

[TestMethod]
public void test_awesome_cats()
{
    Cat Tiger = new Cat();
    Assert.IsTrue(Tiger.CatName.Equals("Tiger"));
}

我尝试将命名约定映射到对象属性中。我弄不明白的部分是MAGICSTUFF.GetInstanceName。这是一件事吗?

我怀疑这是不可能的,所以如果是这样的话,希望有人能给我一些其他聪明的方法,在这种情况下使用约定。我一直在考虑为Cat类使用属性,但我喜欢如果可能的话,这要好得多。

获取它的实例名

这种反射是不可能的。根据调试选项和作用域,编译器可以擦除变量名。变量的名称是其"地址"的别名,因此不能反转(至少在Java和c# AFAIK中)。

一个对象可以从任何变量中指向,所以变量名是无关的,对象不知道这些东西:

Cat tiger = new Cat();
Cat tiger2 = tiger;

变量tiger2指向Cat"老虎",因此2个变量指向同一对象,但名称不同。

使用构造函数中传递的类属性

通常的做法是将'name'作为一个变量存储在实例中,例如:

// Initialize this like: var cat = new Cat("Tiger");
class Cat {
    public String Name { get; private set; }
    public Cat(String name) 
    { 
        Name = name; 
    }
}

然后如果你需要在多个地方得到老虎,把它变成一个显式返回老虎的方法:

// This can go into a class of cat-creating static methods.  Or maybe in the Cat class itself.
public static Cat GiveMeATiger() {
    return new Cat("Tiger");
}

既然问题是这样的,要做到这一点即使不是不可能,也是非常困难的。

使用调试符号,可以挖掘堆栈帧并枚举局部变量,并将地址与实例地址进行匹配。然而,该方法将不起作用,因为构造函数将在引用被设置之前被调用,因此tiger将在当时为空并且匹配将始终失败。

然而,如果我可以改变这个问题,解决方案可能是你需要调用CatName的getter方法中的MAGICSTUFF.GetInstanceName(this);,所以我的方法应该工作得很好。

现在我正试图写一些代码来做到这一点,虽然我会把它张贴在这里,如果有人可能会阅读这篇文章,并在我之前提出真正的实现。

我知道,我知道,老帖子。

但我找到了一个解决方案…

public static List<Packet> Packets = new List<Packet>();
public class Packet
{
    public Packet()
    {
        Packets.Add(this);
    }
    public string packetName;
}
public Packet myPacket = new Packet();
myPacket.packetName = "myPacket";
public void SomeMethod()
{
    int x = 0;
    foreach (Packet p in Packets)
    {
        if (p.packetName = "myPacket")
        {
            Packet myPacket = Packets[x];
            break;
        }
        x++;
    }
}