Как получить ключ ArrayList‹String› из Hashtable?

В основном у меня есть HashTable, содержащая ArrayList<String>,Boolean. Мне нужно получить ключ из Hashtable. Затем мне нужно получить первое значение из ArrayList<String>, которое является ключом.

Я пытался :

    Hashtable<ArrayList<String>,Boolean> tableRows = tableRead(); // returns the Hashtable.

    ArrayList<String> IDs = new ArrayList<String>();        

    Iterator it = tableRows.keySet().iterator();
    while (it.hasNext()) {
        IDs.add(it.next().get(0));      
    }

Однако это дает мне ошибку: cannot find symbol

[javac]   symbol:   method get(int)
[javac]   location: class Object

Просто чтобы дать функциональную идею: у меня есть целая строка БД в качестве ключа в хэш-таблице. Мне нужно вернуть только ID.

Может ли кто-нибудь помочь мне с этим?


person gran_profaci    schedule 09.07.2013    source источник
comment
Какой символ он не может найти?   -  person Sotirios Delimanolis    schedule 10.07.2013
comment
как ваше определение hashTable?   -  person nachokk    schedule 10.07.2013
comment
Поместите общий аргумент в объявление Iterator для нужного типа, т.е. Iterator<ArrayList<String>>.   -  person Sotirios Delimanolis    schedule 10.07.2013
comment
Ну, вы вызываете get на Object, откуда и возникает ошибка компиляции.   -  person thatidiotguy    schedule 10.07.2013
comment
Внес необходимые изменения.   -  person gran_profaci    schedule 10.07.2013
comment
Но мне в основном нужен ключ, не должен ли итератор получить ключ?   -  person gran_profaci    schedule 10.07.2013
comment
@gran_profaci Что за итератор? Компилятор не может знать, пока вы не скажете ему.   -  person Sotirios Delimanolis    schedule 10.07.2013
comment
Понял... спасибо, ребята!   -  person gran_profaci    schedule 10.07.2013
comment
@gran_profaci проверьте мой ответ, нехорошо использовать список в качестве ключа   -  person nachokk    schedule 10.07.2013
comment
@gran_profaci было бы гораздо лучше просто использовать идентификатор в качестве ключа, а не всю строку. Смотрите мой ответ.   -  person Óscar López    schedule 10.07.2013
comment
Да, это правда. Хотя я не мог этого избежать.   -  person gran_profaci    schedule 10.07.2013


Ответы (4)


Вы объявили необработанный Iterator, поэтому его метод next() вернет Object, у которого нет метода get. Это ваш ключ, но он имеет тип Object, потому что ваш Iterator необработан (без параметра общего типа).

Используйте общий Iterator, возвращенный из набора ключей.

Iterator<ArrayList<String>> it = tableRows.keySet().iterator();

Затем it.next() вернет ArrayList<String>, по которому вы можете вызвать get.

person rgettman    schedule 09.07.2013

Вы должны использовать необработанные типы в вашем Iterator

Iterator<ArrayList<String>> it = tableRows.keySet().iterator();

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

Если значение hashCode() объекта может изменяться в зависимости от его состояния, то мы должны быть осторожны при использовании таких объектов в качестве ключей в коллекциях на основе хэшей, чтобы гарантировать, что мы не позволим изменить их состояние, когда они используются в качестве хеш-ключей. . Все коллекции на основе хэшей предполагают, что хеш-значение объекта не изменяется, пока он используется в качестве ключа в коллекции. Если хеш-код ключа изменится, пока он находится в коллекции, могут последовать некоторые непредсказуемые и запутанные последствия. На практике это обычно не проблема — использование изменяемого объекта, такого как список, в качестве ключа в хеш-таблице не является общепринятой практикой.

Если вы все еще хотите сделать коллекцию String неизменяемой таким образом.

List<String> unmodifiableList = Collections.unmodifiableList(myKeyList);

и используйте unmodifiableList в качестве ключа.

person nachokk    schedule 09.07.2013

попробуй это

    ArrayList<String> list = new ArrayList<>();
    Hashtable<ArrayList<String>,Boolean> tableRows = new Hashtable<>();
    Set<ArrayList<String>> keys  = tableRows.keySet();
    Iterator<ArrayList<String>> itr = keys.iterator();
    while(itr.hasNext()){
        itr.next().get(0);
    }

Надеюсь, что это поможет вам.

person Community    schedule 09.07.2013

Использовать ArrayList<String> в качестве ключа к Map — очень и очень плохая идея. Вы никогда не должны использовать изменяемый объект в качестве ключа, если случайно список изменится, ключ будет недействительным - это запах дизайна (и вонючий).

В качестве альтернативы я предлагаю вам создать неизменяемый ключ с конкатенацией строк в ArrayList или использовать неизменяемый список, созданный с помощью Collections.unmodifiableList() или даже лучше, используйте только столбец id, нет смысла использовать всю строку в качестве ключа.

В любом случае, если вам нужно использовать ArrayList в качестве ключа, следующий код решит проблему — и нет необходимости явно использовать итераторы, расширенный цикл for — гораздо лучшая альтернатива для перебора ключей. в таком случае:

for (ArrayList<String> al : tableRows.keySet()) {
    IDs.add(al.get(0));
}
person Óscar López    schedule 09.07.2013