Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/270.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 对象包含与它们所在的上下文相关的信息是否是一种代码气味';重复使用?_C#_Class Design - Fatal编程技术网

C# 对象包含与它们所在的上下文相关的信息是否是一种代码气味';重复使用?

C# 对象包含与它们所在的上下文相关的信息是否是一种代码气味';重复使用?,c#,class-design,C#,Class Design,假设我正在制作一个有很多关卡的游戏,当你在关卡中前进时,新类型的敌人就会出现。如果一个开发者有一个敌人,并且想要得到一个敌人可以被发现的等级,我能想到的最直观的方法是允许他们这样做,那就是在敌人中存储一个等级列表。但我觉得这是个问题,因为现在我已经把我的敌人和我的等级结合在一起了。我的敌人现在知道了它使用的背景。我的研究表明,这种关系对于维护软件是不健康的,但从更高的层次使用它似乎是直观的 下面是一个非常基本的实现: public class Level { List<Enemy&

假设我正在制作一个有很多关卡的游戏,当你在关卡中前进时,新类型的敌人就会出现。如果一个开发者有一个敌人,并且想要得到一个敌人可以被发现的等级,我能想到的最直观的方法是允许他们这样做,那就是在敌人中存储一个等级列表。但我觉得这是个问题,因为现在我已经把我的敌人和我的等级结合在一起了。我的敌人现在知道了它使用的背景。我的研究表明,这种关系对于维护软件是不健康的,但从更高的层次使用它似乎是直观的

下面是一个非常基本的实现:

public class Level
{
    List<Enemy> typesOfEnemies;
    public Level(List<Enemy> typesOfEnemies)
    {
        this.typesOfEnemies = new List<Enemy>(typesOfEnemies);

        for (int i = 0; i < typesOfEnemies.Count; i++)
        {
            typesOfEnemies[i].AddLevelContainedWithin(this);
        }
    }
}

public class Enemy
{
    public List<Level> levelsContainedWithin = new List<Level>();
    public void AddLevelContainedWithin(Level level)
    {
        levelsContainedWithin.Add(level);
    }
}
公共类级别
{
列出敌人的类型;
公共级别(列表类型)
{
this.typesofEquaries=新列表(typesofEquaries);
for(int i=0;i
因此,这段代码可能存在一些问题。最明显的一点是,我可以为敌人添加一个关卡,而不需要更新关卡中的敌人类型,从而使他们失去同步。我可以通过创建另一个类来解决这个问题,确保级别和敌人保持同步,但现在我增加了一层代码复杂性。开发人员现在有另一个类,他们必须知道如何使用它


我的问题是,我如何使它易于维护和直观,以供开发人员使用?

您可以引入另一个实现耦合的类:

class LevelManager
{
    public List<Enemy> GetEnemies(Level l) { ... }
    public List<Level> GetLevels(Enemy e) { ... }
}
类级别管理器
{
公共列表(l级){…}
公共列表GetLevel(敌人e){…}
}
现在,所有数据对象都必须知道
LevelManager


实际上,在你的
敌人
-或你的
等级
-职业中,甚至不需要有这种依赖性。如果开发人员想知道敌人可以在哪个级别生成,他可以使用
LevelManager

我想说这个问题更适合。为什么不使用一个类来管理敌人的哪个级别?因此,您对该管理类具有依赖性,而不是在您的级别和Enemey类中。因此,事实上,每个敌人没有n个级别,而只有一个管理器来管理所有敌人。依赖关系最好是单向依赖关系。比如在应用程序层之间,或者在类之间。为什么你认为你的
敌人
应该知道
等级
?@RomanKalinchuk说谁?孩子认识自己的父亲,父亲也认识自己的孩子,这是绝对正确的。@HimBromBeere说Bob叔叔)不过,你的解决方案看起来很好。我将Levelmanager存储在敌方类中,这样我就可以包装它并创建像敌方.GetLevels这样的简单方法了吗?还是让开发人员习惯于使用LevelManager来完成这些工作更好?在我看来,拥有敌人.GetLevels是非常直观的,不需要开发人员了解LevelManager,但它会创建另一个依赖关系。@SebastianKing我想最干净的方法是不依赖对象类,因为它不是敌人应该关心的。