2015-06-15 8 views
0

У меня странная проблема с моим кодом.Java ArrayList indexOf возвращает -1

Heres код, который я проверить класс Чанк с:

List<Chunk> chunks = new ArrayList<Chunk>(); 
chunks.add(new Chunk(1,1,1)); 
System.out.println(chunks.indexOf(new Vector3i(1, 1, 1))); 

А вот класс Chunk равен метод:

public boolean equals(Object object) { 
    System.out.println("Test _1_"); 
    if (object != null && object instanceof Vector3i) { 
     System.out.println("Test _2_"); 
     if((this.x == ((Vector3i) object).x)&&(this.y == ((Vector3i) object).y)&&(this.z == ((Vector3i) object).z)) { 
      System.out.println("Test _3_"); 
      return true; 
     } 
    } 
    System.out.println("Test _4_"); 

    return false; 
} 

Vector3i:

public class Vector3i { 
    public int x; 
    public int y; 
    public int z; 


    public Vector3i(int x, int y, int z) { 
     this.x = x; 
     this.y = y; 
     this.z = z; 
    } 

} 

Когда я запустите его, он просто возвращает -1. Тестируемые отпечатки с помощью метода equals не печатаются, что означает, что он даже не запускается. Почему это?

+4

Это серьезное злоупотребление [ 'Object.equals()' контракта] (HTTP: // docs.oracle.com/javase/8/docs/api/java/lang/Object.html#equals-java.lang.Object-). Ваш метод 'equals()' не является ** рефлексивным **, ** симметричным ** или ** транзитивным **. Используйте «Map » вместо этого, чтобы связать уникальный кусок с заданным векторным значением. – biziclop

+0

У вас есть класс с именем 'Chunk' с методом' equals', который проверяет, является ли аргумент каким-то другим типом? – MadConan

+0

@MadConan Это потому, что кусок содержит много данных, и это было бы слишком тяжело, если я должен сравнить его с новым. – KaareZ

ответ

5

Если вы проверили цель ArrayList.indexOf, вы увидите, что в вашем случае вызывается Vector3i.equals. На самом деле это даже указано в JavaDoc для List:

Более формально, возвращает наименьший индекс я такой, что (o==null ? get(i)==null : o.equals(get(i))) или -1, если нет такой индекс.

В целом equals операция должна быть симметричной: a.equals(b) == b.equals(a). Таким образом, вы должны реализовать Vector3i.equals.

Обратите внимание, что в вашем текущем equals реализациях не хватает других свойств, таких как рефлексивность. Также рассмотрите возможность применения hashCode при реализации equals.

+0

Спасибо! Это сделало это. – KaareZ

+1

Хотя это на 100% верно, это также ужасный совет. Для начала вы только что нарушили контракт «Object.hashCode()», поэтому я ожидаю «Почему мой« HashMap.get() «возвращает« null »?» вопрос скоро. Во-вторых, он все еще не делает 'equals()' рефлексивным. – biziclop

+1

@biziclop, ну, когда я говорю «equals equals», подразумевается, что неплохо также реализовать hashCode. Что касается других свойств 'equals()' (рефлексивность, транзитивность, согласованность), то это хорошо написано в связанном JavaDoc. Хорошо, я добавлю ответ на ответ. –

0
chunks.indexOf(new Vector3i(1, 1, 1) 

вызовы равна() метод на классе Vector3i, Howeve, а не на класс Chunk ...

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