c# - C#:泛型类中的受保护变量可以由该泛型类的不同子类访问。我可以防止这种情况吗?
问题描述
假设我有一个泛型类 Foo,它有一个受保护的变量
public class Foo<T>
{
protected bool knowsFu;
}
我还有 2 个子类:Bar 和 Pipe
public class Bar : Foo<Bar> {}
public class Pipe : Foo<Pipe> {}
实际上,我可以在 Pipe FROM Bar 中访问 knowFu,例如:
public class Bar : Foo<Bar>
{
void UpdateFuInOtherClass(Pipe p)
{
p.knowsFu = false;
}
}
这是预期的行为吗?(如果是这样,用例会是什么?)
我有没有办法阻止其他 Foo 子类修改/访问我当前子类中的受保护变量?
更具体地说:我使用通用类来实现单例模式: https ://en.wikipedia.org/wiki/Singleton_pattern
但是,我目前可以访问任何单例的受保护实例变量,只要我在另一个单例中。有没有办法防止这种情况?
编辑:可能需要注意受保护的变量(knowsFu)实际上也是静态的。
EDIT2:好的,也许这个例子有点太笼统了..这就是我目前实际实现它的方式:
为什么使用单例?A:我在做的平台是Unity3D,在这个平台上使用的模式比较频繁
我有一个通用类型的抽象类 SingletonBehaviour
public abstract class SingletonBehaviour<T> where T : MonoBehaviour
{
public static T Instance { get { return instance; } }
protected static T instance { get; private set; } }
// Loading is done through Unitys Awake-Method
}
我正在使用的单例对象之一是 APIManager
public class APIManager : SingletonBehaviour<APIManager>
{
// Methods like SendHTTPPost(), HTTPGet(), etc.
}
但是,由于我的大多数项目都需要比这更好的 API 实现,所以我目前正在做的是:
public class ProjectAAPIManager : APIManager
{
// Overriding Instance so my return value is not APIManager but instead ProjectAAPIManager
public static new ProjectAAPIMamager Instance { get { return (ProjectAAPIManager)instance; } }
}
这 ^ 是我的(内部)实例变量受到保护而不是私有的原因。
但是,正因为如此,我项目中的任何其他 SingletonBehaviour 现在都可以访问我的 ProjectAAPIManager 上的(内部)实例变量
public class GameController : SingletonBehaviour<GameController>
{
private void AMethod()
{
// Accessing inner variable instead of public one
ProjectAAPIManager.instance.DoSomething();
}
}
由于它只是吸气剂,因此目前这并不重要。但是,如果我也需要访问我的子类中的设置器怎么办?
另外:通用输入我的 APIManager 是否值得?
解决方案
您不应该有实现通用单例类的类。否则,默认情况下,子类可以访问您的受保护字段(这就是“受保护”关键字的作用)
相反,您应该这样做:
class Program
{
static void Main(string[] args)
{
var barInstance = Foo<Bar>.GetInstance();
}
}
public class Foo<T> where T : new()
{
protected bool knowsFu;
private static T _instance;
public static T GetInstance()
{
if (_instance == null)
_instance = new T();
return _instance;
}
}
public class Bar
{
public Bar()
{
}
}
编辑1:
要使用单例,您不应该让另一个类实现单例行为(这不是单例模式的工作方式)。要使用与第二个示例相同的类,您应该这样做。
public class SingletonBehaviour<T> where T : new()
{
public static T Instance
{
get
{
if(instance == null)
instance = new T()
return instance;
}
}
private static T instance { get; set; }
}
public class APIManager // This class should not inherit from the SingletonBehavior class
{
// Methods like SendHTTPPost(), HTTPGet(), etc.
}
public class ProjectAAPIManager : APIManager
{
public ProjectAAPIManager GetInstance() => SingletonBehavior<ProjectAAPIManager>.Instance();
}
推荐阅读
- javascript - 它是一个正确的正则表达式,有空格并且在`some chancter`之间。?
- react-native - 为什么 flatlist 无法放入容器中 - React Native
- apache-spark - 每个 Micro Batch 中的最大偏移量
- firebase - 通过带有 `--params` 标志的 CLI 安装 Firebase 扩展不会绕过交互式提示
- c# - C# 异步函数 - await 是否立即在新线程上启动任务?
- flutter - 想要在没有按钮的情况下让共享的 pref 工作
- node.js - 如何通过 Yarn Workspaces(使用 CMD)在 Dockerfile 中使用参数?
- css - 显示的ie11布局问题:内联块百分比
- java - 如何更改整个应用程序中的字体大小和字体系列?
- ios - 标记位码(-fembed-bitcode-marker)有什么意义?