Проблемы с переопределением методов и обобщениями в Java - PullRequest
2 голосов
/ 13 сентября 2010

Я боролся с попыткой переопределить метод в общем абстрактном классе.

public abstract class Grandparent<T extends Grandparent>

    public T set(final T other) //does stuff I don't want to do


public abstract class Parent<T extends Parent<T>> extends Grandparent<T>

    public T set(final Parent<?> other) // does stuff I want to do

Все дочерние классы расширяют Parent <child>.

Однако я не могу вызвать нужную мне функцию set (), просто создав один из дочерних классов.

Child_1 test = new Child_1();
Child_1 test_2 = new Child_1();
test.set(test_2) //this calls the function I don't want

Parent<Child_1> test_3 = new Child_1();
Parent<Child_1> test_4 = new Child_1();
test3.set(test_4) //this calls the function I do want

Однако это требует модификации уже существующего кода.Много этого.Я не хочу переписывать метод set в

public T set(T other)

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

Как я могунаписать метод set (), чтобы запускать каждый раз, когда его вызывает дочерний объект, передавая любой другой дочерний объект, без каких-либо изменений во внешнем коде?

Ответы [ 3 ]

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

Чтобы переопределить метод, вам необходимо предоставить эквивалентную переопределению подпись, которая подразумевает, что имя метода, количество и типы аргументов должны быть равны. Это не относится к Grandparent.set() и Parent.set(). Следовательно, Parent.set() перегрузки, а не переопределения, Grandparent.set().

Самое простое решение, которое я вижу, это обобщить сигнатуры методов следующим образом:

public abstract class Grandparent<T extends Grandparent>
    public T set(Grandparent<?> other) 

public abstract class Parent<T extends Parent<T>> extends Grandparent<T>
    public T set(Grandparent<?> other) 

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

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

Последующие комментарии помогли уточнить, что вы ищете, но я все еще могу быть озадачен. Возможно, это поможет; если нет, пожалуйста, попробуйте уточнить ваш вопрос.

public abstract class Grandparent<T extends Grandparent<T, Q>, Q extends Grandparent<T, Q>>
{

  public abstract Q set(Q other);

}

class Parent<T extends Parent<T>>
  extends Grandparent<T, Parent<T>>
{

  @Override
  public Parent<T> set(Parent<T> other)
  {
    throw new UnsupportedOperationException("set");
  }

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

Как я могу написать метод set () для запускать каждый раз, когда дочерний объект вызывает это, передавая в любой другой дочерний объект, без каких-либо изменений снаружи код

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

EDIT

Классы, с которыми я тестировал ...

package test.stack.overflow;

public abstract class GrandParent<T extends GrandParent>
{
    public T set(final GrandParent<?> other)
    {
        System.out.println("GrandParent.set=" + other);

        return null;
    }
}

public abstract class Parent<T extends Parent<T>> extends GrandParent<T>
{
    public Parent<?> set(final Parent<?> other)
    {
        System.out.println("Parent.set=" + other);

        return other;
    }
}

public class Child_1 extends Parent<Child_1>
{
}

public class Child_2 extends Parent<Child_2>
{
}

public class TestPeerage
{    
    public static void main(String[] args)
    {
        Child_1 c1 = new Child_1();

        c1.set(new Child_2());
        c1.set(new Child_1());

        Parent<Child_1> pc1 = new Child_1();

        pc1.set(new Child_2());
        pc1.set(new Child_1());
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...