[英]How to get a list of specific fields values from objects stored in a list?
假設我有一個對象列表,其中包含兩個字段field1
和field2
,兩者都是String類型。
如果可能的話,如何獲取所有field1
值的列表而不必迭代列表?
幸運的是,您可以使用Java 8 - Streams執行此操作
假設您有一個名為YourEntity的實體
public class YourEntity {
private String field1;
private String field2;
public YourEntity(String field1, String field2) {
this.field1 = field1;
this.field2 = field2;
}
public void setField1(String field1) {
this.field1 = field1;
}
public void setField2(String field2) {
this.field2 = field2;
}
public String getField1() {
return field1;
}
public String getField2() {
return field2;
}
}
使用以下內容聲明YourEntity列表:
List<YourEntity> entities = Arrays.asList(new YourEntity("text1", "text2"), new YourEntity("text3", "text4"));
您可以通過以下方式一次性提取field1的列表:
import java.util.stream.Collectors;
List<String> field1List = entities.stream().map(YourEntity::getField1).collect(Collectors.toList());
或者以這種方式
import java.util.stream.Collectors;
List<String> field1List = entities.stream().map(urEntity -> urEntity.getField1()).collect(Collectors.toList());
您也可以使用java 8打印所有項目:)
field1List.forEach(System.out::println);
產量
text1
text3
試試這個:
List<Entity> entities = getEntities();
List<Integer> listIntegerEntities = Lambda.extract(entities, Lambda.on(Entity.class).getFielf1());
LambdaJ允許訪問沒有顯式循環的集合,因此不要讓更多的代碼行自己迭代列表,而是讓LambdaJ去做。
對象是對存儲器地址的引用。 然后,此對象的字段是對其他內存地址的其他引用。 因此,對象列表是引用列表。 因此,列表不可能直接訪問對象字段(引用給出的引用)。 最簡潔的答案是不。
注意:無論如何,你會找到一個能夠滿足您需求的API,它仍然會在內部循環。
java作為一種語言,JDK庫都沒有做你想做的事。 您可以使用LambdaJ或等待預期包含lambda表達式的Java 8。
...你的問題是否avoiding iterating over the collection
:
具體來說,你的意思是:
請參閱下面的解決方案和選項。
如果它是第一個,那么請查看Google Guava,LambdaJ,FunctionalJava或其他實現基本功能構造的庫,並允許您在一些富有表現力的調用中執行您想要的操作。 但請記住,這些可以做到錫上的內容:它們將過濾,收集或轉換集合,並將迭代其元素來執行此操作。
例如:
谷歌番石榴 :
Set<String> strings = buildSetStrings(); Collection<String> filteredStrings = Collections2.filter(strings, Predicates.containsPattern("^J"));
功能Java :
Array<Integer> a = array(97, 44, 67, 3, 22, 90, 1, 77, 98, 1078, 6, 64, 6, 79, 42); Array<Integer> b = a.filter(even);
LambdaJ :
List<Integer> biggerThan3 = filter(greaterThan(3), asList(1, 2, 3, 4, 5));
如果它是第二個,那么這是不可能的 , 除非您從一開始就構建了所有內容,以便您的對象應該由自定義集合類管理,該集合類將根據插入時的字段值索引對象 。
它會將它們保存在由所述值索引的桶中,以便您可以將它們作為列表檢索或按需設置。
正如下面的評論中提到的那樣dounyy的答案,設計這樣的自定義集合可能會對它接受的元素的API產生影響(最有可能通過定義用於元素類型的超級接口),或者需要相當復雜的實現如果您希望此集合是通用的,則動態地解析成員(最有可能通過使用反射)。
古老的問題,但我想看看我是否可以改進類似的解決方案。
您可以實現List<String>
接口,而無需創建充實的ArrayList<String>
,因此不會迭代父對象。
final List<Entity> entities = getEntities()
final List<String> field1 = new AbstractList() {
public String get(int index) {
return entities.get(index).getField1();
}
public int size() {
return entities.size();
}
}
這為您提供了一個List而不迭代父對象。
對派生List<String>
隨機訪問將與對基礎List<Entity>
隨機訪問一樣昂貴; 如果您使用的List<Entity>
實現不提供快速隨機訪問,您可能需要跳過幾個環節(即實現List<String>
更多方法。但這應該適用於99%的你需要一個輕量級適配器的情況。
是!! 這是可能的。 但你必須做一些彎曲的工作。
使用必需的變量創建內部類。 例如:這里將使用2個變量。(TNAME和TABTYPE)。
public class storeTables { private String tablename = ""; private String tabletype = ""; public storeTables(String a, String b) { this.setTablename(a); this.setTabletype(b); } public void setTablename(String tablename) { this.tablename = tablename; } public String getTablename() { return tablename; } public void setTabletype(String tabletype) { this.tabletype = tabletype; } public String getTabletype() { return tabletype; }}
創建上面創建的內部類的列表,不要忘記封裝它。
private List<storeTables> objlist= new ArrayList<storeTables>();
獲取存儲在列表中的值作為內部類對象。
String Query="SELECT * FROM TAB"; while(rs.next()) { String tname=rs.getString("TNAME"); String tabtype=rs.getString("TABTYPE"); getObjlist().add(new storeTables(tname,tabtype)); }
創建一個DATAMODEL並將列表推送到datamodel
private DataModel selectableItems= new ListDataModel(objlist);
將warpped數據轉換到另一個列表。
List<storeTables> items= (List<storeTables>)selectableItems.getWrappedData();
最后!!! 打印數據。
for(storeTables item:items){ System.out.println(item.getTablename()); }
TADA !!!! 它只會打印tablename而不是tabtype;)相信java中沒有什么不可能有任何疑問!!
不,你不能。 您必須遍歷整個列表並從每個對象獲取每個“field1”值。
也許你可以用這種方式創建一個hashmap:
HashMap<String, ArrayList<Object>> map;
關鍵是這個領域。 這樣做時,當您要求HashMap檢索對應於您想要的字段的對象時,該映射將返回一個ArrayList,其中包含具有該字段的所有元素。
沒有迭代,這是不可能的。你可以以某種方式減少迭代,但這是必須的。
在不同的列表中添加記錄的值,並使用一個或兩個迭代器只需打印單獨的值。如下所示:
rs=st.executeQuery("select * from stu");
List data=new ArrayList();
List data1=new ArrayList();
while(rs.next())
{
data.add(rs.getString(1));
data1.add(rs.getString(2));
}
Iterator it=data.iterator();
Iterator it1=data1.iterator();
while(it1.hasNext())
{
System.out.println(" "+it.next()+" "+it1.next());
}
讓對象屬於以下類。
public class Bike {
String bikeModel;
Int price;
}
現在有名為BikeList的自行車清單列表
所以現在我們想要上面列表中所有自行車的自行車模型列表。
bikeList.map{ Bike b -> b.bikeModel }.toCollection(arrayListOf())
返回bikeList中所有自行車對象的第一個字段的數組列表
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.