1

为了好玩,我想用Java制作一个篮球模拟游戏。我想要一个简单的类“团队”,我想要一个名为“玩家”的类团队的子类。我了解如何声明类和子类,但我的问题是如何向某个团队声明球员?

例如:

Team team1 = new Team();
Team team2 = new Team();
Player nameHere = new Player();

如何将其设置为 Team1 或 team2 上的 Player nameHere 等...

4

6 回答 6

2

您需要了解两个重要的软件设计原则:

- Inheritance (IS A relationship)

- Composition (HAS A relationship)

当您处理第一个概念时,您使用类和子类。但在这种情况下,您的子类本质上与您的父类相同:它就像一辆汽车和法拉利。Ferrari IS A car(这种关系在 OOP 中以继承表示)。然而,汽车有挡风玻璃。挡风玻璃不是汽车,它是汽车的一部分(这种关系表现为包含一个类作为另一类的字段成员 - 组合)。现在,您了解了这些关系,您需要问自己一个问题:球员A队,还是球队A球员?

在这种情况下,这似乎很明显。您需要在班级List<Player>内放置一个。Team

于 2013-11-08T23:06:36.690 回答
1

我不认为你完全理解继承意味着什么。超类的子类应该是超类的特例。

查看http://docs.oracle.com/javase/tutorial/java/IandI/subclasses.html了解更多示例。

你想要的是一个有魅力的班级团队

List<Player> players;

如果您想编写任何面向对象的代码,我建议您阅读继承。

于 2013-11-08T23:02:10.447 回答
1

其他人提供了很好的解释,但让我补充一点。

许多没有经验的开发人员使用子类化来保存代码。他们对在学校学到的继承非常着迷,以至于他们急于将所有东西都分解到某个通用的基类中,然后疯狂地对其进行子类化。

那是错误的做法。

一个类应该继承另一个类而不是如果它们共享代码,而是如果它们共享相同的行为。所以问问你自己,一个球员和一个球队有同样的行为吗?

可能不是。

例如,一个球队有一个时间表、一个对手名单、一个老板、一个城市、一个出席人数、一个体育场等等。玩家没有。所以Player不应该子类化Team。但是, A像其他人提到的那样Team由 a 组成是有意义的。List<Player>

但是现在让我们把它变得更加复杂和有趣。

让我们考虑一个足球队。球队中的一名球员可以有进球、助攻和犯规。球队也可以拥有所有这些东西,球队对这些东西的价值是所有球员的这些价值的总和。但是,与其使用继承,不如使用称为(蹩脚的名字,我知道)之类的接口为您提供更好的服务,并同时拥有并实现该接口。假设有一个方法。那么如果客户说MeasurableTeamPlayerMeasurablegetGoals()

int goals = measurable.getGoals();

客户不知道也不关心他是否获得了球队或球员的进球数——只是对象知道它有多少个进球。

这实际上是Composite Pattern的一个例子。

所以底线是不Player应该 sublcas Team,而Team应该由它们组成,Player因为它们有不同的行为。但是,如果它们确实具有名称、目标等共同属性,则使用接口将其表示为描述完全不同类型对象的通用方式。

于 2013-11-08T23:22:46.540 回答
0

这样做

class Player {

//player properties and setter , getter

}

class Team{

  List<Player> players = new ArrayList<Player>();

  // setter and getter  
}

将球员加入球队

Team t1= new Team();

Player p1 = new Player(); 
Player p2 = new Player();
Player p3 = new Player();

t1.getPlayers().add(p1);
t1.getPlayers().add(p2);
t1.getPlayers().add(p3);
于 2013-11-08T23:05:05.690 回答
0

你需要类似的东西。

class Team {
    List<Player> players;

    Team() {
        players = new ArrayList<Player>();
    }

    public void addPlayer(Player p) {
        players.add(p);
    }
}

这就是您创建和添加Player到的方式Team

Player player1 = new Player();
Player player2 = new Player();
Team team1 = new Team();
team1.addPlayer(player1);
team1.addPlayer(player2);

要知道的是inheritance (is a)composition(has a)关系。

希望这可以帮助。

于 2013-11-08T23:05:27.290 回答
0

如果您将您Team视为Players 的容器,您的Team类将有一个包含Players 的属性,以及用于添加、删除、清除等的访问器方法Team

当然,您的Team类将有自己的属性和方法,可能会从Player您在团队中拥有的任何数据(例如玩家数量等)中获取数据。

在这种情况下,没有与继承相关的主题

您的课程只有容器与“容器”关系(Artem 的回答使用了正确的术语)。

例如:

class Team {
    // the private property containing the players
    // I use a Set here because each player is unique
    private Set<Player> players;
    public Team() {
        // initializing the set as HashSet
        players = new HashSet<Player>();
    }
    public void addPlayers(Player... players) {
        // adding all players
        for (Player p: players) {
            this.players.add(p);
        }
    }
    public Collection<Player> getPlayers() {
        // returning a copy of the team's players
        return new HashSet<Player>(players);
    }
}
class Player {
    // TODO player's properties such as name, age, feats, etc.
}

然后你会像这样添加Players Team

Team t = new Team();
// adding single player
t.addPlayers(new Player());
// adding an array of players
t.addPlayers(new Player[]{new Player(), new Player()});
于 2013-11-08T23:07:49.847 回答