У меня есть приложение Java, которое использует JPA.Как лучше всего обращаться Список <Entity>, Список <Entity Id>, Список <Entity name> эффективно?
Скажем, у меня есть объект под названием Product
с name
и price
атрибутов (все объекты имеют атрибут id
).
Естественно, я могу получить List<Product>
довольно легко (из запроса или другого объекта), но часто я хочу List<String>
(список названий продуктов) или List<Long>
(список цен на продукцию или список идентификаторов продукта).
Много времени это так же легко пройти весь Product
вокруг, но есть два случая, когда я не хочу, чтобы это сделать:
- Я передаю список в классе который не должен зависеть от класса
Product
. - Значительно проще/быстрее получить список идентификаторов, чем полные объекты продукта (но в некоторых случаях у меня уже есть).
Наивный способ сделать это бы что-то вроде:
List<Long> productIds = new ArrayList<Long>();
for(Product product: products) {
productIds.add(product.getId());
}
Но мне не нравится это, потому что это грязно и неэффективно. В Python я хотел бы сделать что-то вроде:
[ p.id for p in products ]
"Лучший" Я могу придумать в Java является:
public class ProductIdList extends AbstractList<Long> {
private List<Product> data;
public ProductIdList(List<Product> data) {
this.data = data;
}
public Long get(int i) {
return data.get(i).getId();
}
public int size() {
return data.size();
}
public Long remove(int i) {
return data.remove(i).getId();
}
/* For better performance */
public void clear() {
data.clear();
}
/* Other operations unsupported */
}
Плюсы:
- Этот подход не нужно скопируйте данные
- Это истинный «вид» на данные - отражаются изменения в базовом списке.
Минусы:
- Кажется, что много кода
- нужен класс, как это для каждого атрибута Я хочу, чтобы получить доступ, как этот
Так это хорошо идея или нет? Должен ли я просто создавать вторичные списки большую часть времени? Есть ли третий вариант, который я не рассматривал?
Положив комментарий не ответ. Просто небольшой совет, вы всегда можете получить только идентификаторы продукта, а не весь продукт (используя то, что я слышал, называемый скалярным запросом). Например. SELECT prod.id FROM Product prod ... –
Точно. Возможно, я должен был быть яснее. Иногда я могу это сделать, и проблем нет. Иногда у меня уже есть Список и не хочу требовать. –
Draemon
Вы можете использовать один класс, который имеет один метод для каждого атрибута. Это уменьшило бы одну CONS. – StampedeXV