views:

349

answers:

1

Hello World,

I have a JTree in which the user can drag/drop or re-arrange nodes, upon saving I have to re-arrange the nodes such that File type nodes must appear before Folder type nodes. I don't need to sort the files/folders name.

User Tree:

 -FolderA
   +FFA1
   -FA1
   -FA2
 -FolderB
   -FB1
 -File1
 -File2
 +FolderC
 -File3

Resulting Tree:

-File1
 -File2
 -File3
 -FolderA   
   -FA1
   -FA2
   +FAF1
 -FolderB
   -FB1
 +FolderC

I have the following codes below, it worked but I don't know if it is the proper way or the good practice perhaps. Can you suggest which of the 2 solutions is better, or can you suggest other way.

Thanks you very much.

Solution 1:

private void arrange(DefaultMutableTreeNode parent){
 DefaultMutableTreeNode sorted = new DefaultMutableTreeNode();
 List<DefaultMutableTreeNode> files = new ArrayList<DefaultMutableTreeNode>();
 List<DefaultMutableTreeNode> folders = new ArrayList<DefaultMutableTreeNode>();

 for (int i = 0; i < parent.getChildCount(); i++){
  DefaultMutableTreeNode node = (DefaultMutableTreeNode) parent.getChildAt(i);
  int type = ((BusinessObject) node.getUserObject()).getType();
  if (type == BusinessObject.FILE)
   files.add(node);
  else{
   arrange(node);
   folders.add(node);
  }
 }
 for (int i = 0; i < files.size(); i++)
  sorted.add((DefaultMutableTreeNode) files.get(i));

 for (int i = 0; i < folders.size(); i++)
  sorted.add((DefaultMutableTreeNode) folders.get(i));

 while (sorted.getChildCount() > 0)
  parent.add((DefaultMutableTreeNode) sorted.getChildAt(0));

 sorted = null;
 files = null;
 folders = null;
}

Solution 2:

private void arrange(DefaultMutableTreeNode parent){
 DefaultMutableTreeNode sorted = new DefaultMutableTreeNode();
 List<DefaultMutableTreeNode> nodes = new ArrayList<DefaultMutableTreeNode>();

 for (int i = 0; i < parent.getChildCount(); i++){
  DefaultMutableTreeNode node = (DefaultMutableTreeNode) parent.getChildAt(i);
  int type = ((BusinessObject) node.getUserObject()).getType();
  if (type == BusinessObject.FILE)
   nodes.add(node);
 }

 for (int i = 0; i < parent.getChildCount(); i++){
  DefaultMutableTreeNode node = (DefaultMutableTreeNode) parent.getChildAt(i);
  int type = ((BusinessObject) node.getUserObject()).getType();
  if (type == BusinessObject.FOLDER){
   arrange(node);
   nodes.add(node);
  }
 }

 for (int i = 0; i < nodes.size(); i++)
  sorted.add((DefaultMutableTreeNode) nodes.get(i));

 while (sorted.getChildCount() > 0)
  parent.add((DefaultMutableTreeNode) sorted.getChildAt(0));

 sorted = null;
 nodes = null;
}
+1  A: 

I think both are fine solutions. It was pretty easy to tell what they were doing: pull out the files, pull out the folders, throw them back in the tree in the right order. Also, the recursive call was straight-forward and intuitive.

Pick whichever seems the most natural to you. The second seems more like the way I would do it, but that's just me, and there's not much difference.

Are you using Java 5 or 6? If so, use for-each loops. Also, you don't have to clear that values of your private variables at the end of the method. They go away anyhow when the method returns.

Jeremy Stein
Thanks Jeremy, I am also thinking of #2 is better because there is only one instance of the list is created.
jerjer