Расширение класса в Java - PullRequest
       2

Расширение класса в Java

3 голосов
/ 08 сентября 2010

У меня есть список таких объектов

ArrayList <Page> pageList = aForeignObject.getAllPages();

и детский класс

class MyPage extends Page
{

    public void newFunction()
    {
        // A new Feature
    }
}

Возможно ли как-то преобразовать объекты Page в объекты MyPage?

Я бы хотел сделать что-то вроде этого:

MyPage page = pages.get(1); // This will obviously fail 
page.newFunction();

Ответы [ 4 ]

4 голосов
/ 08 сентября 2010

Если объекты Page, выходящие из метода getAllPages(), на самом деле являются MyPage объектами, то просто используйте приведение (например, MyPage page = (MyPage) pages.get(1);. Если это не так (как, вероятно, если вы используете внешний код), вы не можете использовать подклассы. Однако вы можете использовать состав:

class MyPage{
    private Page p;

    public MyPage(Page aPage){
        p = aPage;
    }

    public void newFunction(){
        //stuff
    }

    public Object oldFunction(){
        return p.oldFunction();
    }
}

Тогда вы можете сделать что-то вроде:

MyPage page = new MyPage(pages.get(1));
page.newFunction();
1 голос
/ 08 сентября 2010

Краткое решение - приведение:

MyPage page = (MyPage)pages.get(1);

Обратите внимание, что для этого требуется, чтобы рассматриваемый объект действительно имел тип MyPage - в противном случае приведение завершится неудачно с ClassCastException.Если вы не уверены в этом, вы можете сначала проверить тип объекта:

Page elem = pages.get(1);
if (elem instanceof MyPage) {
  MyPage page = (MyPage)elem;
  ...
}

Однако необходимость делать такие откаты часто является признаком того, что дизайн вашего класса может быть улучшен.Если aForeignObject.getAllPages() всегда возвращает список MyPage объектов, вы должны соответственно изменить его тип возвращаемого значения.В противном случае, если newFunction имеет смысл в интерфейсе Page (даже абстрактном или с пустой реализацией по умолчанию), вам следует рассмотреть возможность его добавления;тогда вы можете позвонить newFunction напрямую по Page ссылкам без необходимости снижения.

Обновление: , поэтому у вас есть Page объекты, которые вы хотите преобразовать в MyPage объекты ... Техническим решением для этого будет преобразование Конструктор :

class MyPage extends Page {
  MyPage(Page other) {
    // deep copy internal state
  }
  ...
}

Хотя технически это работает, я все же переосмыслил бы подход к проектированию, который требует таких решений, если это возможно.Если вы используете сторонний код, который вы не можете изменить, это не вариант.

0 голосов
/ 08 сентября 2010

Я думаю, что решение состоит в том, чтобы реализовать вашу "новую функцию" в Page.У меня также было несколько таких ситуаций, и для меня решение было реализовано в базовом классе.Но я не знаю точно, в какой ситуации вы находитесь ...

Второе решение (не рекомендуется): сделать вашу "новую функцию" статическим методом.Примерно так:

public static void feature(Page page)
{
     ....
}

Затем вы можете сделать ярлык в MyPage:

public void invokeFeatureMethod()
{
     feature(this);
}
0 голосов
/ 08 сентября 2010

Это явно грязно, но может работать ...

Page page = pages.get(1);
if (page instanceof MyPage) {
  ((MyPage)page).newFunction();
}

Вы можете хранить список всех классов, которые extends Page, т.е.

List <? extends Page> pageList = aForeignObject.getAllPages(); //Bear in mind that Page objects will never be found here.

Теперь, если список содержит только MyPage, вы можете использовать мой пример выше. Как я уже сказал, это не эффективное и не эффективное решение.

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