【问题标题】:How can I determine the type of object that is allowed to call specific method?如何确定允许调用特定方法的对象类型?
【发布时间】:2012-04-17 01:08:26
【问题描述】:

我有一个Node 类:

public class Node
{
    private string name;
    private Point3D location;
    private int id;
    .
    .
}

还有一个Graph 类:

public class Graph
{
  ....
}

Node 中的 id 是只读的,但我只需要从 Graph 对象而不是从 Graph 类之外设置它的值。我怎样才能做到这一点?

【问题讨论】:

  • "节点类中的 id 是只读的,但我只需要从 Graph 对象中设置它的值" 这听起来像是一个糟糕的设计。将节点 ID 保持只读是一件好事,但是一旦程序的任何部分尝试更改节点 ID,您就会失去不变性的好处。
  • 这个问题很不清楚。请考虑改进它。
  • @AdamMihalcin 如果 id 是只读的,一旦初始化,其他东西怎么能改变它?实际上,在使实体不可变时,您需要将字段标记为只读。
  • @DarthVader 当然,您不能更改只读字段。我是说放弃只读并引入突变是一个坏主意。但是,您不需要将字段标记为只读以使对象不可变。如果您定义了一个密封类,其属性都具有公共 get 和私有 set,并且除了构造函数之外什么都使用 setter,那么您没有使用 readonly 关键字,但是您已经构建了一个其对象不能被任何外部改变的类代码。

标签: c# class access-modifiers


【解决方案1】:

一个可能帮助(但不是完全修复它)的选项是在属性上使用修饰符internal。这将属性的可访问性范围限制在它所属的程序集内,以及声明为朋友的任何程序集内。

话虽如此,您将 Id 公开但只能从 Graph 对象更改的要求违反了 OO 概念。解决此问题的一种方法是将 Node 对象的创建限制在 Graph 类中,或者从仅可用于 Graph 类的工厂方法中创建。如果你这样做并且只使用一个 getter 将 Id 属性公开为公共,并在构造函数中为其分配一个值,那么你将实现 90% 的目标。

【讨论】:

    【解决方案2】:

    您可以使Node 类成为Graph 类的私有嵌套类,因此只有Graph 类可以访问和修改它,您可以使用Graph 类中的公共方法访问图形节点的方法

    【讨论】:

    • 我认为将Node 设为私有嵌套类并不是很有用。您应该可以直接从外部使用它。
    • @svick 您可以通过 Graph 类的公共方法使用它。但这只是一个想法。我不知道你在想什么。
    • 这是内部使用的方法,例如 XmlWriter 的抽象工厂实现。这无疑是一种有效的方法,但需要一个可公开访问的抽象基类(假设它应该完全公开)。
    【解决方案3】:
    public NameSpace{
        public class Node{
          public int Id { get; internal set; }
          // rest of the code...
        }
    
        public class Graph{
          // Node Id can be set here...
        }
    }
    

    这行得通吗?

    【讨论】:

      猜你喜欢
      • 2018-10-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多