我试图在Java中创建游戏SeaBattle,请参阅下面的类图。
船上的船只的视觉表现通过给船舶覆盖深色的油田的细胞而发生。
为了放置一艘船,我会将它称为段() - 方法并给它它的坐标。为了便于稍后通过点击它所放置的单元格来选择正确的段,我认为最好是单元格包含对同一段的引用。
我所面临的实施问题在于拆除船舶:应该可以根据船舶的指令拆卸船舶(简单:循环通过它的段并取消它们,也移除它们它们所在的单元格中的引用,但也可以通过单击船舶(即:在网格中的其中一个段上)来实现。每当发生这种情况时,我都知道点击了哪个段,但我需要弄清楚该段属于哪个船只,以便取消其他段。
我可以获取单击的单元格坐标,遍历所有船只及其段并检查坐标是否匹配,但我觉得有更好的方法。也许甚至可以更好地设置类图的一部分。
答案 0 :(得分:1)
我们可以将Ship
字段添加到ShipSegment
,并使ShipSegment
成为Cell
的子类。这是一个可能的实现:
public class Battlefield {
Cell[][] cells;
public Battlefield(int size) {
this.cells = new Cell[size][size];
for (int x = 0; x < size; x++) {
for (int y = 0; y < size; y++) {
cells[x][y] = new Cell();
}
}
}
public void add(Ship ship) {
int start = ship.horizontal ? ship.x : ship.y;
for (int i = 0; i < ship.size(); i++) {
cells[ship.horizontal ? i + start : ship.x][ship.horizontal ? ship.y : i + start] = ship.getSegment(i);
}
}
public void remove(Ship ship) {
int start = ship.horizontal ? ship.x : ship.y;
for (int i = start; i < start + ship.size(); i++) {
cells[ship.horizontal ? i : ship.x][ship.horizontal ? ship.y : i] = new Cell();
}
}
public boolean shoot(int x, int y) {
return cells[x][y].shoot();
}
}
public class Cell {
private boolean isShot;
public Cell() {
this.isShot = false;
}
public boolean isEmpty(){
return true;
}
public boolean isShot(){
return isShot;
}
public boolean shoot() {
isShot = true;
return isEmpty();
}
}
public class ShipSegment extends Cell {
Ship ship;
public ShipSegment(Ship ship) {
super();
this.ship = ship;
}
@Override
public boolean isEmpty() {
return false;
}
public Ship getShip() {
return ship;
}
}
public class Ship {
int x, y;
boolean horizontal;
ShipSegment[] segments;
public Ship(int x, int y, int size, boolean horizontal) {
this.x = x;
this.y = y;
this.horizontal = horizontal;
segments = new ShipSegment[size];
for (int i = 0; i < size; i++) {
segments[i] = new ShipSegment(this);
}
}
public int size() {
return segments.length;
}
public boolean isDestroyed() {
for (ShipSegment segment : segments) {
if (!segment.isShot()) {
return false;
}
}
return true;
}
public ShipSegment getSegment(int index){
return segments[index];
}
}