2012-09-30 5 views
1

Я читал об этом, вместо того, чтобы использовать методы instanceof и getClass для реализации полиморфизма, поскольку это лучше объектно-ориентированная практика.Как я могу использовать полиморфизм здесь для улучшения моего кода?

Если моя программа выглядит следующим образом:

Piece 
SlowPiece extends Piece, 
FastPiece extends Piece, 
SlowFlexible extends SlowPiece, 
FastFlexible extends FastPiece 

И я следующее правило: SlowPiece's can only move one space, and FastPiece's as many as they'd like.

Как бы использовать polymorphism, чтобы гарантировать, что если я двигаюсь Кусок как Piece piece1 = new SlowPiece(); что это не перемещается более одного?

У меня есть класс для игрового поля, и он должен иметь возможность перемещать кусок, но я не уверен, как остановить его от перемещения SlowPiece более 1 без обнюхивания кода.

В принципе, я понимаю, как полиморфизм фантастический, скажем, перечисляя вещи, но на самом деле взаимодействуя с ними, я не понимаю, как правильно его использовать.

+1

Я бы сказал, что отправка вручную * никогда * не показывает полиморфизм (любого типа), но .. –

+1

В любом случае, почему бы не просто метод int intNumberNumberOfSpaces() {..} '? Кроме того, рассмотрите * интерфейсы * для контрактов (подклассирование - это просто простой способ совместного использования поведения). –

ответ

4

Сделайте Piece аннотация и добавьте абстрактный метод move() в Piece (вы также можете использовать интерфейс пользователя). Внесите move() по-разному (a SlowPiece перемещает только 1 место и т. Д.).

public abstract class Piece { 
    public abstract void move(); 
} 

public class SlowPiece extends Piece { 
    public void move() { 
     System.out.println("moving a slow piece"); 
    } 
} 

public class FastPiece extends Piece { 
    public void move() { 
     System.out.println("moving a fast piece"); 
    } 
} 

Piece f = new FastPiece(); 
f.move();  

Piece s = new SlowPiece(); 
s.move(); 

Здесь move() имеет всю движущуюся логику; вы могли бы даже использовать некоторые перегрузки, чтобы обеспечить разнообразие движения (например, взять N/S/W/E в качестве аргументов и т. д.).

+0

Поскольку кусок должен обладать знаниями о доске, это невозможно, если я не получаю совет каждый раз, не так ли? Мне нужно убедиться, что этот шаг не будет толкать его с края доски (поэтому я должен проверить индексы 2D-массива) и убедиться, что в настоящее время другие части не занимают место, на которое оно намеревается перейти. Я в большой степени рассматривал этот вариант, но я не видел, как я мог заставить его двигаться, если бы я не знал, где еще на доске он может двигаться. –

+0

Вы должны, вероятно, сделать все элементы 'Piece' объекта 'Game' (который, в свою очередь, также содержит объект' Board'), чтобы разрешить перекрестный доступ. Опять же, это всего лишь один шаблон, но для меня это кажется интуитивным. –

+0

Если вы не хотите использовать более крупный объект (который может перерасти в объект Бога), используйте инъекцию зависимостей (это другой шаблон). –

1

Больше, чем полиморфизм, вы, вероятно, должны думать об ответственности.

Вы класс «совет» должен делать только что-то вроде

piece.move(); 

и кусок должен знать, как двигаться. Так что если у вас есть как кости вы можете перейти к методу перемещения количества и действовать соответственно, как

piece.move(moves); 

EDIT:

совет должен управлять движениями, так что возвращение метод перемещения int шагов, сделанных куском. Движение должно управляться из другого класса, такого как доска, а не из самой части.

Предлагаю вам очень интересную книгу об анализе OO: «Применение uml и узоров» Крейга Лармана. Он содержит также пошаговый пример настольной игры как монополии!

+0

Поскольку кусок должен иметь знания о доске, это невозможно, если я не получаю совет каждый раз, не так ли? Мне нужно убедиться, что этот шаг не будет толкать его с края доски (поэтому я должен проверить индексы 2D-массива) и убедиться, что в настоящее время другие части не занимают место, на которое оно намеревается перейти. –

+0

Концептуально кусок не должен иметь знания о доске, потому что это всего лишь кусок. Сделайте метод move возвратом int, чтобы понять, сколько шагов выполнило и управляет этой информацией с вашей доской. :) – Enrichman

3

В качестве еще одного соображения по этой проблеме, давайте разобраться в общей общей концепции.

  • A Piece can move().
  • Определенные типы Piecemove() в отличие от других.

В качестве интерфейса можно объявить Piece и использовать все остальные Piece s.Таким образом, вы являетесь , гарантируя, что каждый Piece имеет move(), а также заставляет вас следить за тем, чтобы каждый move() отличался в зависимости от Piece.

+0

Другой способ - сделать «Piece» абстрактным классом. Это было бы более легко, если бы были другие распространенные методы и не позволяло вам кодировать общие только –

+1

Этот аспект уже хорошо освещен в ответе Дэвида Титаренко. Это зависит от того, что вы пытаетесь выполнить с вашими объектами, и как (в) конкретном вы хотите получить с ними. – Makoto

Смежные вопросы