This problem should not use DFS to solve it, I have tried, but failed with this test case: [3,9,8,4,0,1,7,null,null,null,2,5]
My output is: [[4],[9,5],[3,0,1],[2,8],[7]]
But it was expected: [[4],[9,5],[3,0,1],[8,2],[7]]
Because the problem's request is: ...return the vertical order traversal of its nodes' values. (i.e., from top to bottom, column by column)
private Map<Integer, List<Integer>> map = new HashMap<>(); public List<List<Integer>> verticalOrder(TreeNode root) { List<List<Integer>> res = new ArrayList<>(); helper(root, 0); List<Integer> keys = new ArrayList<>(); for(int i:map.keySet()){ keys.add(i); } Collections.sort(keys); for(int i: keys){ res.add(map.get(i)); } return res; } private void helper(TreeNode root, int level){ if(root==null) return; map.putIfAbsent(level, new ArrayList<>()); map.get(level).add(root.val); helper(root.left, level-1); helper(root.right, level+1); }
The following is my BFS solution:
1. I used an object NodeCol to store both TreeNode and it's column. You can use two Queues too.
2. I sorted the Map's key to get the column from small to big. You can maintain a min and max to store minimal column and maximal column too.
class Solution { class NodeCol{ public TreeNode node; public int col; public NodeCol(TreeNode node, int col){ this.node = node; this.col = col; } } private Map<Integer, List<Integer>> map = new HashMap<>(); public List<List<Integer>> verticalOrder(TreeNode root) { List<List<Integer>> res = new ArrayList<>(); if(root==null) return res; Queue<NodeCol> queue = new LinkedList<>(); queue.offer(new NodeCol(root, 0)); while(!queue.isEmpty()){ NodeCol nc = queue.poll(); map.putIfAbsent(nc.col, new ArrayList<>()); map.get(nc.col).add(nc.node.val); if(nc.node.left!=null) queue.offer(new NodeCol(nc.node.left, nc.col-1)); if(nc.node.right!=null) queue.offer(new NodeCol(nc.node.right, nc.col+1)); } List<Integer> keys = new ArrayList<>(); for(int i:map.keySet()){ keys.add(i); } Collections.sort(keys); for(int i: keys){ res.add(map.get(i)); } return res; } }
The following is my improved BFS solution, beat 100%
1. Uses two Queues intead of a private class
2. Don't have to sort map's keys.
public List<List<Integer>> verticalOrder(TreeNode root) { List<List<Integer>> res = new ArrayList<>(); if (root == null) return res; int min = 0, max = 0; Map<Integer, List<Integer>> map = new HashMap<>(); Queue<TreeNode> queue = new LinkedList<>(); Queue<Integer> levelsQ = new LinkedList<>(); queue.offer(root); levelsQ.offer(0); while (!queue.isEmpty()) { int size = queue.size(); for (int i = 0; i < size; i++) { TreeNode node = queue.poll(); int level = levelsQ.poll(); min = Math.min(min, level); max = Math.max(max, level); map.putIfAbsent(level, new ArrayList<>()); map.get(level).add(node.val); if (node.left != null) { queue.offer(node.left); levelsQ.offer(level - 1); } if (node.right != null) { queue.offer(node.right); levelsQ.offer(level + 1); } } } for (int i = min; i <= max; i++) { res.add(map.get(i)); } return res; }