Интерфейс SortedMap
SortedMap – наследник интерфейса Map, описывает ассоциативный массив, элементы которого упорядочены по ключам. Методы, предоставляемые этим интерфейсом: firstKey(), lastKey(), subMap(Object fromKey, Object toKey),headMap(Object toKey), tailMap(Object fromKey) аналогичны методам интерфейса SortedSet. Данный интерфейс реализуется, например, в классе TreeMap. Один из конструкторов этого класса принимает объект типа Comparator, посредством которого можно задать свой собственный порядок сортировки.
Пример работы с ассоциативными массивами
Необходимо разработать метод findUser(String login, String password), находящий в базе данных зарегистрированных пользователей пользователя с логином login и паролем password и возвращающий объект класса User, созданный на основе информации из этой БД. Метод должен возвращать null, если пользователя с требуемыми логином и паролем не существует.
Сведения о зарегистрированных пользователях хранятся в таблице USERS, имеющей следующую структуру:
Также имеется вспомогательный метод getNextUser(), который возвращает очередную строку этой таблицы, а если строк больше нет, возвращает null. Заголовок этого метода может выглядеть следующим образом:
Map getNextUser();
Заметьте, возвращаемый результат имеет интерфейсный тип Map, а не какого-то конкретного класса (например,Hashtable). Это профессиональный подход к разработке метода. Конечно, внутри метода происходит работа с объектом конкретного класса (возможно, с тем же Hashtable – ведь метод должен создать возвращаемый объект, а создать объект абстрактного класс или интерфейса нельзя). Но, скрывая детали своей реализации и сообщая остальной программе лишь минимально необходимую информацию (что возвращаемый результат поддерживает интерфейс Map), метод добивается большей гибкости. Впоследствии может быть принято решение заменить Hashtable на HashMap, и при этом все изменения нужно будет произвести только в теле метода getNextUser(), а не во всех местах программы, где он вызывался.
Ключами элементов ассоциативного массива, возвращаемого методом getNextUser(), являются строки, совпадающие с названиями столбцов таблицы, а значениями – строки, содержащие значения из соответствующей ячейки таблицы. Предположим, что этот метод к тому же облегчает нам работу: заменяет значение 0 столбца category на строку «user», а значение 1 на строку «admin». Дело в том, что в зависимости от категории пользователя (которая в БД закодирована числом), мы должны создать либо объект класса User, либо объект производного от него класса Admin.
Метод будет выглядеть следующим образом.
private User findUser(String login, string password) {
Map userData = getNextUser();
while (userData != null) {
if (((String)UserData.get("login")).equals(login) &&((String)UserData.get("password")).equals(password)) {
if (((String)UserData.get("category")).equals("user"))
return new User((String)UserData.get("name"));
if (((String)UserData.get("category")).equals("admin"))
return new Admin((String)UserData.get("name"));
}
userData = getNextUser();
}
return null;
}
Обратите внимание как каждый раз, обращаясь к ассоциативному массиву userData методом get() и получая значение, ассоциированное с нужным нам ключом, мы приводим его к типу String.
Обратите внимание на организацию цикла while: мы вызываем метод getNextUser(), пока он не возвратит нам значение null. Если в процессе обработки очередного набора данных из таблицы мы обнаружим, что логин и пароль совпадают с параметрами метода, мы завершаем работу метода командой return, возвращая требуемый объект. Если же команда return ни разу не вызовется в цикле, это будет означать, что такого пользователя в базе нет и метод должен вернуть null, что он и делает в последней строке.
Классы-оболочки
Объектно-ориентированный подход к описанию коллекций дает нам ряд преимуществ. В частности, возможность помещать в коллекции объекты любых классов. Но при этом простые типы данных оказываются обделенными. Мы не можем создать коллекцию целых чисел int или символов char*.
Для того, чтобы работать с простыми типами данных как с объектами (и, в частности, применять их в коллекциях), используются так называемые классы-оболочки (wrappers). Класс-оболочка построен по очень простому принципу: он хранит внутри себя поле простого типа и предоставляет несколько операций для доступа к этому полю.
В стандартной библиотеке Java определены восемь классов-оболочек – по одному на каждый простой тип. Их названия совпадают с названиями этих типов, но начинаются с заглавной буквы. То есть, это Byte, Short, Long, Float, Double,Char, Boolean. Исключение – класс-оболочка для целых чисел, который называется Integer. Каждый класс имеет простой конструктор, принимающий величину соответствующего типа.
Integer i = new Integer(15);
Boolean b = new Boolean(false);
При необходимости можно получить «содержимое» класса с помощью одного из его методов. Автоматического приведения к простому типу не происходит. Так что, если необходимо передать в какой-то метод параметр типа int, а нужное нам число представляет собой объект класса Integer, надо осуществить явное преобразование:
String s;
сhar ch = s.charAt(i.intValue);
Можно добавлять объекты простых типов в любую коллекцию. Например:
Vector vect = new Vector();
vect.add(b);
vect.add(new Double(3.14));
Класс Vector в последних версиях Java позволяет передавать в метод и примитивные типы данных, автоматически создавая для них оболочку.
Дата добавления: 2017-01-26; просмотров: 1192;