Home > database >  Get all leaves elements of a recursive nested structure Data in java
Get all leaves elements of a recursive nested structure Data in java

Time:02-05

How can I get all leaves elements of a recursive nested structure Data?

public class Item {
    private String id;
    private List<Item> items;
}

Exemple:

    A
      - AA
        - aa1
      - AB
        - ab1
          - abab1 
      - a1

Result

In the result I need to get only the following list of elements [aa1, abab1, a1]

CodePudding user response:

You can do it quite easily in a recursive fashion:

public static List<Item> findLeaves(Item rootItem){
    List<Item> leaves = new ArrayList<>();
    recursivelyCollectLeaves(leaves, rootItem);
    return leaves;
}

private static void recursivelyCollectLeaves(List<Item> leaves, Item actualItem){
    if(actualItem.getItems().isEmpty()){
        //No children, the actual item is a leaf
        leaves.add(actualItem);
    }
    else{
        for(Item child : actualItem.getItems()){
            recursivelyCollectLeaves(leaves, child);
        }
    }
}

PS: In order to make this code work, please note that I added getters to the Item class.

CodePudding user response:

How about adapting Item like this:

public static class Item {
    private final String id;
    private final List<Item> items;

    public Stream<Item> getLeaves() {
        if (items == null || items.isEmpty()) {
            return Stream.of(this);
        }
        return items.stream()
            .flatMap(Item::getLeaves);
    }

}

Which you can then use as:

final var item = new Item(
    "A",
    List.of(
        new Item("AA",
            List.of(new Item("aa1"))
        ),
        new Item("AB",
            List.of(new Item("ab1",
                List.of(new Item("abab1")))
            )
        ),
        new Item("a1")
    )
);

final var leaves = item.getLeaves()
    .map(Item::getId)
    .collect(Collectors.toList());

System.out.println(leaves);

Note: constructors and getters omitted for brevity

CodePudding user response:

Try adding this method to the class:

public List<Item> getLeaves() {
    ArrayList<Item> list = new ArrayList<>();
    if (items.size() == 0) {
        list.add(this);
    } else {
        for (Item item : items) {
            list.addAll(item.getLeaves());
        }
    }
    return list;
}

It just checks if itself is a leaf. If it is, it returns itself, if not, it returns all of the leaves of its children.

  •  Tags:  
  • Related