[英]Convert a POJO to Tree structure in Java 8 for representation of data in hierarchical structure
我有一個List<CropDetailDto>
由postgresql 中本機查詢的Hibernate Projection返回。
我想以分層/樹格式表示它以將其作為響應發送。
我在List<CropDetailDto>
上使用了多個嵌套的Collectors.groupingBy
public Map<String, Map<String, Map<String, List<CropDetailDto>>>> findCropDetails() {
List<CropDetailDto> cropdetails = cropRepository.getCropDetails();
return cropdetails.stream().collect(Collectors.groupingBy(CropDetailDto::getCropName, Collectors.groupingBy(
v -> v.getVarietyName() == null ? "undefined" : v.getVarietyName(),
Collectors.groupingBy(m -> m.getSubVarietyName() == null ? "undefined" : m.getSubVarietyName()))));
}
我以某種方式能夠以這種格式表示數據。
{
"Tomato": {
"Red Tomato": {
"Red Tomato 1 quality": [
{
"cropName": "Tomato",
"varietyName": "Red Tomato",
"subVarietyName": "Red Tomato 1 quality",
"varietyId": 1002,
"cropId": 1,
"subVarietyId": 1003 //cropDetailDto is again represented
//at the leaf level
}
],
"Red Tomato 2 quality": [
{
"cropName": "Tomato",
"varietyName": "Red Tomato",
"subVarietyName": "Red Tomato 2 quality",
"varietyId": 1002,
"cropId": 1,
"subVarietyId": 1004
}
]
}
},
"Brinjal": {
"undefined": {
"undefined": [
{
"cropName": "Brinjal",
"varietyName": null,
"subVarietyName": null,
"varietyId": null,
"cropId": 8,
"subVarietyId": null
}
]
}
}
}
但是,這種表示undefined
為鍵,因為它為空鍵拋出了 NPE。
我想以更清晰的格式表示相同的數據。
像這樣的東西:
{
"Tomato": {
"Red Tomato": [
"Red Tomato 1 quality",
"Red Tomato 2 quality"
]
},
"Brinjal": {}
}
即,如果有一個空鍵,我希望它移動到下一個條目。
我最近開始使用java 8,我正在尋找一種簡潔的方法來實現上述結構。
CropDetailDto:
public interface CropDetailDto {
Long getCropId();
String getCropName();
Long getVarietyId();
String getVarietyName();
Long getSubVarietyId();
String getSubVarietyName();
}
結果返回類型也可以是一個簡單的HashMap<String, Object>
。 此外,如果使用Java 8 功能無法實現此目的,請提供一種無需Java 8即可實現此目的的方法。
提前致謝。
您可以使用Collectors.mapping()
而不是最后一個Collectors.groupingBy()
:
public Map<String, Map<String, List<String>>> findCropDetails() {
List<CropDetailDto> cropdetails = cropRepository.getCropDetails();
return cropdetails.stream().collect(Collectors.groupingBy(CropDetailDto::getCropName,
Collectors.groupingBy(v -> v.getVarietyName() == null ? "undefined" : v.getVarietyName(),
Collectors.mapping(m -> m.getSubVarietyName() == null ? "undefined" : m.getSubVarietyName(),
Collectors.toList()))));
}
這將返回以下地圖:
{
"Tomato": {
"Red Tomato": [
"Red Tomato 1 quality",
"Red Tomato 2 quality"
]
},
"Brinjal": {
"undefined": [
"undefined"
]
}
}
要從結果中刪除null
值,您可以使用Collectors.filtering()
並稍微修改上面的代碼:
public Map<String, Map<String, List<String>>> findCropDetails() {
List<CropDetailDto> cropdetails = cropRepository.getCropDetails();
return cropdetails.stream().collect(Collectors.groupingBy(CropDetailDto::getCropName,
Collectors.filtering(v -> v.getVarietyName() != null, Collectors.groupingBy(CropDetailDto::getVarietyName,
Collectors.filtering(m -> m.getSubVarietyName() != null, Collectors.mapping(CropDetailDto::getSubVarietyName,
Collectors.toList()))))));
}
使用它,最終結果將如下所示:
{
"Tomato": {
"Red Tomato": [
"Red Tomato 1 quality",
"Red Tomato 2 quality"
]
},
"Brinjal": {}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.