I am currently learning a bit about streams. I have the following JSONArray, and I want to be able to retrieve all the distinct xvalues.
datasets: {
ds1
What you get with .map(dataset -> dataset.getJSONArray("xvalues")
(try-catch
block omitted for sake of clarity) is a list itself and the subsequent call of distinct
is used on the Stream<List<Object>>
checking whether the lists itself with all its content is same to another and leave distinct lists.
You need to flat map the structure to Stream<Object>
and then use the distinct
to get the unique items. However, first, you need to convert JSONArray to List.
List<String> xvalues = arrayToStream(datasets)
.map(JSONObject.class::cast)
.map(dataset -> dataset -> {
try { return dataset.getJSONArray("xvalues"); }
catch (JSONException ex) {}
return;})
.map(jsonArray -> toJsonArray(jsonArray )) // convert it to List
.flatMap(List::stream) // to Stream<Object>
.distinct()
.collect(Collectors.toList());
I believe using a json library(Jackson, Gson) is the best way to deal with json data. If you can use Jackson, this could be a solution
public class DataSetsWrapper {
private Map<String, XValue> datasets;
//Getters, Setters
}
public class XValue {
private List<String> xvalues;
//Getters, Setters
}
ObjectMapper objectMapper = new ObjectMapper();
DataSetsWrapper dataSetsWrapper = objectMapper.readValue(jsonString, DataSetsWrapper.class);
List<String> distinctXValues = dataSetsWrapper.getDatasets()
.values()
.stream()
.map(XValue::getXvalues)
.flatMap(Collection::stream)
.distinct()
.collect(Collectors.toList());
Replace jsonString with your json. I tested this with this json
String jsonString = "{\"datasets\": {\n" +
" \"ds1\": {\n" +
" \"xvalues\": [\n" +
" \"(empty)\",\n" +
" \"x1\",\n" +
" \"x2\"\n" +
" ]\n" +
" },\n" +
" \"ds2\": {\n" +
" \"xvalues\": [\n" +
" \"(empty)\",\n" +
" \"x1\",\n" +
" \"x2\",\n" +
" \"x3\"\n" +
" ]\n" +
" }\n" +
"}}";