2010-06-24 2 views
9

У меня проблема с ArrayList. Я использую ArrayList, как это:ArrayList indexOf() возвращает неверный индекс?

private ArrayList<Playlist> mPlaylists; 

где Playlist класс наследуется от другого ArrayList. я сделать следующее:

p = new Playlist(...some parameters...); 
mPlaylists.add(p); 

Позже, когда я использую «р», чтобы получить индекс в списке:

int index = mPlaylists.indexOf(p); 

индекс «1» возвращается, даже если инспекция из список ясно показывает, что это индекс «4».

Кто-нибудь знает, почему это не удается? Спасибо.

B.R. Morten

Edit: же проблема без IndexOf(), с помощью равенства():

private int GetIndex(Playlist playlist) { 
    for (int i = 0; i < mPlaylists.size(); i++) { 
     if (mPlaylists.get(i).equals(playlist)) { 
      return i; 
     } 
    } 
    return -1; 
} 

правка: Это работает !:

private int getIndex(Playlist playlist) { 
    for (int i = 0; i < mPlaylists.size(); i++) { 
     if (mPlaylists.get(i) == playlist) { 
      return i; 
     } 
    } 
    return -1; 
} 

Решение: Как и было предложено, я изменил класс Playlist, чтобы не допустить это из ArrayList, а скорее для хранения экземпляра в частном порядке. Оказалось, что мне нужно было реализовать только 4 метода ArrayList.

Это трюк; Теперь indexOf() возвращает правильный объект!

Спасибо всем участникам!

+5

Что находится в mPlaylists.get (1); ? Вы переопределили 'equals()' в 'Playlist' - что-нибудь напугало? –

+0

Включает ли список воспроизведения список индекса ArrayList? –

+1

Мой первоначальный ответ: «у вас нет, вы думаете, что у вас есть», а затем «один p ​​считает, что это другой p (или не знает, что это такое)». – 2010-06-24 20:46:00

ответ

7

Скорее всего, ваш PlayList перепутались с реализацией в ArrayList по умолчанию equals, потому что путь indexOf является calculated к чему-то вроде:

indexOf(Object o) 
    if(o == null) then iterate until null is found and return that index 
    if(o != null) iterate until o.equals(array[i]) is found and return taht index 
    else return -1 
end 

Таким образом, вы делаете что-то смешное с методом .equals или ваш являются случайно в Если вы считаете, что это конец, добавьте еще один элемент в список.

EDIT

В соответствии правки ... см? Ваш метод .equals() не работает.

Рассмотреть возможность сделать хороший обзор и убедитесь, что он прилипает к описанию, определенное в Object.equals

+0

+1: Ударьте меня к ней на минуту –

+0

Как и в вашем новом редактировании, вы выполняете сравнение ссылок, из-за чего я думаю, что вы на самом деле не наследуете ArrayList.Похоже, что вы делаете что-то действительно странное с этим классом «PlayList» (например, с использованием прописных имен методов yiack ...) – OscarRyz

+0

Хе-хе, да - но, по крайней мере, используя имя метода верхнего регистра, я не забуду, что это всего лишь тестовый метод , с целью устранения этой проблемы :-) Спасибо! –

-1

Я не уверен, почему вы с этой проблемой, но я думаю, что если бы я тебя, я бы выбрал использовать новую Generic List, чтобы создать свой список, как это:

List<Playlist> mPlaylists = new List<Playlist>(); 

p = new Playlist(<some parameters>); 
mPlaylists.Add(p); 
+0

Невозможно создать экземпляр списка .. не смог проголосовать, хотя из сегодняшних голосов ;-) –

+0

ОП использует общую форму - просто а не интерфейс List, но реализация ArrayList. Хотя он не полностью чист, это обычно считается закрытым членом класса. Когда вы написали просто не компилируете - вы не можете создать экземпляр List - это интерфейс. Поместите «ArrayList» в правой части задания, и все будет хорошо. – mdma

+0

@ Lauri - никогда не бойтесь, у меня остались голоса> :-) Russ - это даже не компилируется, и не отвечает на вопрос. –

1

От API:

int indexOf(Object o):

Возвращает индекс первого вхождения указанного элемент в этом списке, или -1, если этот список не содержит этот элемент. Более формально возвращает самый низкий индекс i такой, что (o==null ? get(i)==null : o.equals(get(i))), или -1, если такого индекса нет.

Таким образом, ответ заключается в том, что вам необходимо переопределить .equals() в Playlist.

+0

Он не должен, если он действительно наследует 'ArrayList', потому что этот метод уже переопределен для этого класса. Итак, предложение было бы ** не **, чтобы снова переопределить его (или сделать это правильно) – OscarRyz

+0

Хм ... Так что я сделал; Наследовать от ArrayList, а не переопределять equals(), должен работать? ... –

0

Там может быть много причин для такого поведения:

1) Если несколько элементов в качестве ArrayList равны (по методу равен), то первый один возврат. Возможно, у вас просто несколько идентичных объектов.

2) Ваш класс PlayList расширяет ArrayList (я не уверен, что это хорошая идея). Поэтому, если вы не переопределили метод equals, сравнение основывается только на последовательности элементов. Например, любые два пустых экземпляра PlayList будут считаться равными.

3) Если вы переопределили равные, проверьте свою реализацию. Он должен возвращать true для сравнения с той же ссылкой, и в вашем случае это не так.

+0

Я вижу вашу точку зрения, но поскольку я не переопределял equals(), и есть некоторые члены String, которые отличаются друг от друга, я все равно не ожидал, что они появятся как «равные»? –

+1

@Morten Priess: Каков был тип элементов в PlayList? Какова была реализация equals() для этого типа? Если PlayList просто содержит объекты String, я не могу объяснить это поведение. –

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