C# 一种类型如何访问另一种类型的私有setter';谁的财产?

C# 一种类型如何访问另一种类型的私有setter';谁的财产?,c#,access-modifiers,C#,Access Modifiers,我所需要的只是一种方法,使一个类的属性只能从另一个类(一种管理器类)中“设置” 这在c#中可能吗 我的同事“可靠地”告诉我,我有一个设计缺陷,但我觉得我至少应该在承认失败之前询问社区 不,在C#中以任何干净的方式都不可能做到这一点。您可能有设计缺陷;-) 不,在C#中以任何干净的方式都不可能做到这一点。您可能有设计缺陷;-) 是否是设计缺陷取决于您想做什么。您可以使用System.Diagnostics中的StackTrace类来获取设置属性的类的类型,然后与您希望允许设置或属性的类型进行比较。

我所需要的只是一种方法,使一个类的属性只能从另一个类(一种管理器类)中“设置”

这在c#中可能吗


我的同事“可靠地”告诉我,我有一个设计缺陷,但我觉得我至少应该在承认失败之前询问社区

不,在C#中以任何干净的方式都不可能做到这一点。您可能有设计缺陷;-)

不,在C#中以任何干净的方式都不可能做到这一点。您可能有设计缺陷;-)

是否是设计缺陷取决于您想做什么。您可以使用System.Diagnostics中的StackTrace类来获取设置属性的类的类型,然后与您希望允许设置或属性的类型进行比较。但是,如果是设计缺陷,可能有更好的方法来执行类似操作(例如装箱)

。您可以使用System.Diagnostics中的StackTrace类来获取设置属性的类的类型,然后与您希望允许设置或属性的类型进行比较。但是可能有更好的方法来执行类似的操作(例如装箱)

您不能这样做,但是您可以从派生类访问属性的setter方法,因此可以使用继承。您所要做的就是放置受保护的访问修改器。如果您尝试这样做,您的同事是对的:)。您可以尝试这样做:

public string Name
{
    get{ return _name; }
    protected set { _name = value; }
}

请记住,属性的set方法只能从派生类访问。

这样做是不可能的,但可以从派生类访问属性的setter方法,因此可以使用继承。您所要做的就是放置受保护的访问修改器。如果您尝试这样做,您的同事是对的:)。您可以尝试这样做:

public string Name
{
    get{ return _name; }
    protected set { _name = value; }
}

请记住,属性的set方法只能从派生类访问。

您可以通过在“可设置类”中创建一个公共属性来实现这一点,该属性将从具有受保护属性的真实类继承。。。这样,只有继承类可以设置,而不是不继承的类。但缺点是您需要有一个继承类…

您可以通过在“可设置类”中创建一个公共属性来实现这一点,该属性将继承具有受保护属性的真实类。。。这样,只有继承类可以设置,而不是不继承的类。但是缺点是您需要有一个继承类…

,或者您可以在一个程序集中单独有这两个类,并将setter作为内部类。尽管如此,我还是会投票赞成设计缺陷,除非milot之前的回答(继承和保护)是有意义的。

或者您可以将这两个类单独放在一个程序集中,并将setter作为内部的。尽管如此,我还是会投票赞成设计缺陷,除非milot之前的回答(继承和保护)有意义。

您可以使用
internal
修饰符,该修饰符允许同一程序集中的所有类型访问数据(如果使用
[InternalsVisibleTo],则指定程序集)
-但是没有:C#中没有与之相当的
朋友

例如:

public string Foo {get; internal set;}

您可以使用
internal
修饰符,该修饰符允许同一程序集中的所有类型访问数据(如果使用
[InternalsVisibleTo]
,则可以访问指定的程序集)-但否:C#中没有
friend
等效项

例如:

public string Foo {get; internal set;}

你有一个设计缺陷。另外,不要对数据隐藏心存疑虑。下面是3.5的方法:

class Program
    {
        static void Main(string[] args)
        {
            Managed m = new Managed();
            Console.WriteLine(m.PrivateSetter);
            m.Mgr.SetProperty("lol");
            Console.WriteLine(m.PrivateSetter);
            Console.Read();
        }
    }

    public class Managed
    {
        private Manager _mgr;
        public Manager Mgr
        {
            get { return _mgr ?? (_mgr = new Manager(s => PrivateSetter = s)); }
        }
        public string PrivateSetter { get; private set; }
        public Managed()
        {
            PrivateSetter = "Unset";
        }
    }

    public class Manager
    {
        private Action<string> _setPrivateProperty;
        public Manager(Action<string> setter)
        {
            _setPrivateProperty = setter;
        }
        public void SetProperty(string value)
        {
            _setPrivateProperty(value);
        }
    }

你有一个设计缺陷。另外,不要对数据隐藏心存疑虑。下面是3.5的方法:

class Program
    {
        static void Main(string[] args)
        {
            Managed m = new Managed();
            Console.WriteLine(m.PrivateSetter);
            m.Mgr.SetProperty("lol");
            Console.WriteLine(m.PrivateSetter);
            Console.Read();
        }
    }

    public class Managed
    {
        private Manager _mgr;
        public Manager Mgr
        {
            get { return _mgr ?? (_mgr = new Manager(s => PrivateSetter = s)); }
        }
        public string PrivateSetter { get; private set; }
        public Managed()
        {
            PrivateSetter = "Unset";
        }
    }

    public class Manager
    {
        private Action<string> _setPrivateProperty;
        public Manager(Action<string> setter)
        {
            _setPrivateProperty = setter;
        }
        public void SetProperty(string value)
        {
            _setPrivateProperty(value);
        }
    }
你可以做:

public void setMyProperty(int value, Object caller)
{
    if(caller is MyManagerClass)
    {
        MyProperty = value;
    }
}
这意味着您可以使用调用类中的“This”指针。我会质疑您试图实现的逻辑,但在不知道具体情况的情况下,我无法进一步给出建议。我要说的是:如果可以重构代码以使其更清晰,那么这样做通常是值得的

但这是相当混乱,当然不是傻瓜证明…你已经被警告了

交替地

您可以将具有属性(类a)的类的委托传递给Manager类(类B)。委托可以引用a中的私有函数,以允许B将该委托作为任何普通函数调用。这排除了a知道B以及a可能是在B之前创建的。同样,这是一个混乱且不易出错的问题!

您可以执行以下操作:

public void setMyProperty(int value, Object caller)
{
    if(caller is MyManagerClass)
    {
        MyProperty = value;
    }
}
这意味着您可以使用调用类中的“This”指针。我会质疑您试图实现的逻辑,但在不知道具体情况的情况下,我无法进一步给出建议。我要说的是:如果可以重构代码以使其更清晰,那么这样做通常是值得的

但这是相当混乱,当然不是傻瓜证明…你已经被警告了

交替地


您可以将具有属性(类a)的类的委托传递给Manager类(类B)。委托可以引用a中的私有函数,以允许B将该委托作为任何普通函数调用。这排除了a知道B以及a可能是在B之前创建的。同样,这是一个混乱且不容易出错的问题!

最好的方法是:

/// <summary>
/// Gets or sets foo
/// <b>Setter should only be invoked by SomeClass</b>
/// </summary>    
public Object Foo
{
    get { return foo; }
    set { foo = value; }
}
//
///获取或设置foo
///Setter只能由SomeClass调用
///     
公共对象Foo
{
获取{return foo;}
设置{foo=value;}
}
当您有一些复杂的访问或继承限制,并且强制执行这些限制要求代码太复杂时,有时候最好的方法就是正确地对其进行注释

但是请注意,如果此限制具有某些安全含义,则不能依赖此限制,因为您取决于将使用此代码的开发人员的善意。

最好的方法是