2017-03-06 75 views
1

我有這個項目中,我的程序從操作系統的磁盤映像提取文件,並存儲在數據庫中的細節和其他功能獲取在從數據庫文件,並將其存儲節點列表(我自己的對象類型),應該在獲取路徑(也存儲在數據庫中)之後創建JTree,並根據斜線拆分路徑字符串,以便各種文件夾中的文件是葉節點,文件夾是父項。文件的抓取工作完美,但我認爲創建JTree有些問題,因爲某些文件夾在JTree中顯示爲葉節點。下面是截圖:JTree的是顯示應該是可擴展的葉子節點

you can see the /home and /usr folders are terminal nodes

讓我告訴你我的代碼是什麼樣子:

public class ActiveCase { 
private void populateList(){ 
    //a function that fetches a list of files from a database and stores it in a list 
List<AbstractFile> l = *a query function that stores the files in the list*; 
listFiles(l); 
} 

public void listFiles(List<AbstractFile> fl){  
    ArrayList<TreePath> te = new ArrayList<TreePath>(); 
    try {   
     for(AbstractFile file : fl){ 
     //don't worry about the isDir() and getName() functions they work        
     if(!file.isDir() && !file.getName().startsWith(".")){           
     te.add(new TreePath(("File list"+formatPath(file.getUniquePath())).split("/"))); 
     } 
    } 
    } catch (TskCoreException e) { 
     // TODO Auto-generated catch block 
     e.printStackTrace(); 
    } 

     TreeModel tmClean = new TreePathsTreeModel("File list", te); 
     cleanPanel.add(new JTree(tmClean)); 
} 

private static String formatPath(String uniquePath){ 
    String[] pathSegments = uniquePath.split("/"); 
    int index = 3; 
    StringBuilder strbuf = new StringBuilder(); 
    for (; index < pathSegments.length; ++index) { 
     if (!pathSegments[index].isEmpty()) { 
      strbuf.append("/").append(pathSegments[index]); 
     } 
    } 
    return strbuf.toString(); 
}   

}

而且我已經得到了實現TreeModel的一個TreePathsTreeModel類:

public class TreePathsTreeModel implements TreeModel { 
     private final ArrayList<TreePath> paths; 
     private final String root; 

     public TreePathsTreeModel(String root, ArrayList<TreePath> te) { 
     this.root = root; 
     this.paths = te; 
     //a little test print statement to see if the TreePath list is in the right format 
     for(TreePath t : paths){ 
      System.out.println(t.toString()); 
     } 
     } 
     @Override 
     public Object getRoot() { 
     return this.root; 
     } 

     @Override 
     public Object getChild(Object parent, int index) { 
     try { 
      return getChildren(parent).get(index); 
     } catch (IndexOutOfBoundsException ex) { 
      return null; 
     } 
     } 

     @Override 
     public int getChildCount(Object parent) { 
     return getChildren(parent).size(); 
     } 

     @Override 
     public boolean isLeaf(Object node) { 
     for (int i = 0; i < paths.size(); i++) { 
      TreePath treePath = paths.get(i); 
      if (treePath.getLastPathComponent().equals(node)) 
      return true; 
     } 
     return false; 
     } 

     // This method is only required for editable trees, so it is not 
     // implemented here. 
     @Override 
     public void valueForPathChanged(TreePath path, Object newValue) { 
     //throw new UnsupportedOperationException("Not supported yet."); 
     } 

     @Override 
     public int getIndexOfChild(Object parent, Object child) { 
     return getChildren(parent).indexOf(child); 
     } 

     // This TreeModel never fires any events (since it is not editable) 
     // so event listener registration methods are left unimplemented 
     @Override 
     public void addTreeModelListener(TreeModelListener l) { 
     //throw new UnsupportedOperationException("Not supported yet."); 
     } 

     @Override 
     public void removeTreeModelListener(TreeModelListener l) { 
     //throw new UnsupportedOperationException("Not supported yet."); 
     } 
       //search all paths in list for given object 
       //return every item one level further than it 
     private ArrayList<String> getChildren(Object parent) { 
     ArrayList<String> children = new ArrayList<String>(); 
     for (int i = 0; i < this.paths.size(); i++) { 
      ArrayList<Object> pathObjects = new ArrayList<Object>(Arrays.asList(this.paths.get(i).getPath())); 
      for (Iterator<Object> it = pathObjects.iterator(); it.hasNext();) { 
      Object parentCandidate = it.next(); 
      if (parentCandidate.equals(parent)) { 
       Iterator<Object> checker = it; 
       try { 
       String child = new DefaultMutableTreeNode(checker.next()).toString(); 
       if (!children.contains(child)) 
        children.add (child); 
       } catch (NoSuchElementException ex) { 

       } 
      } 
      } 
     } 
     return children; 
     } 

    } 

據我可以從打印statemen告訴在TreePathsTreeModel構造函數中,列表格式是正確的。我會粘貼下面的輸出示例:

... 
[File list, dev, tty0] 
[File list, dev, tty1] 
[File list, dev, tty2] 
[File list, dev, tty3] 
[File list, dev, tty4] 
[File list, dev, tty5] 
[File list, dev, tty6] 
[File list, dev, tty7] 
[File list, dev, tty8] 
[File list, dev, tty9] 
[File list, dev, urandom] 
[File list, dev, zero] 
[File list, home, mainvm, examples.desktop] 
[File list, home, mainvm, .cache, wallpaper, 0_5_1920_950_792beab7550410d531e55f95b449f135] 
[File list, home, mainvm, .cache, upstart, unity7.log.2.gz] 
[File list, home, mainvm, .cache, upstart, ssh-agent.log.2.gz] 
[File list, home, mainvm, .cache, upstart, gnome-keyring-ssh.log.1.gz] 
[File list, home, mainvm, .cache, upstart, dbus.log] 
[File list, home, mainvm, .cache, upstart, unity7.log] 
[File list, home, mainvm, .cache, upstart, hud.log] 
[File list, home, mainvm, .cache, upstart, upstart-event-bridge.log.2.gz] 
[File list, home, mainvm, .cache, upstart, unity7.log.1.gz] 
[File list, home, mainvm, .cache, upstart, unity-settings-daemon.log.2.gz] 
[File list, home, mainvm, .cache, upstart, unity-panel-service.log.2.gz] 
[File list, home, mainvm, .cache, upstart, hud.log.1.gz] 
[File list, home, mainvm, .cache, upstart, window-stack-bridge.log.2.gz] 
[File list, home, mainvm, .cache, upstart, gpg-agent.log.2.gz] 
[File list, home, mainvm, .cache, upstart, ssh-agent.log.1.gz] 
[File list, home, mainvm, .cache, upstart, window-stack-bridge.log.1.gz] 
[File list, home, mainvm, .cache, upstart, unity-panel-service.log] 
[File list, home, mainvm, .cache, upstart, unity-settings-daemon.log.1.gz] 
[File list, home, mainvm, .cache, upstart, unity-panel-service.log.1.gz] 
[File list, home, mainvm, .cache, upstart, dbus.log.2.gz] 
[File list, home, mainvm, .cache, upstart, dbus.log.1.gz] 
[File list, home, mainvm, .cache, upstart, gnome-keyring-ssh.log.2.gz] 
[File list, home, mainvm, .cache, upstart, gpg-agent.log.1.gz] 
[File list, home, mainvm, .cache, upstart, indicator-sound.log.2.gz] 
[File list, home, mainvm, .cache, upstart, indicator-sound.log.1.gz] 
[File list, home, mainvm, .cache, upstart, upstart-event-bridge.log.1.gz] 
[File list, home, mainvm, .cache, ibus, bus, registry.F0VAPY] 
... 
[File list, home, mainvm, .local, share, recently-used.xbel.49E0TY] 
[File list, home, mainvm, .local, share, recently-used.xbel] 
[File list, home, mainvm, .gnupg, gnupg_spawn_agent_sentinel.lock] 
[File list, home, mainvm, .gnupg, S.gpg-agent] 
[File list, lib, apparmor, functions] 
[File list, lib, apparmor, profile-load] 
[File list, lib, brltty, brltty.sh] 
[File list, lib, brltty, libbrlttybal.so] 
[File list, lib, brltty, libbrlttybat.so] 
[File list, lib, brltty, libbrlttybba.so] 
[File list, lib, brltty, libbrlttybbc.so] 
[File list, lib, brltty, libbrlttybbd.so] 
[File list, lib, brltty, libbrlttybbg.so] 
[File list, lib, brltty, libbrlttybbl.so] 
[File list, lib, brltty, libbrlttybbm.so] 
[File list, lib, brltty, libbrlttybbn.so] 
[File list, lib, brltty, libbrlttybcb.so] 
[File list, lib, brltty, libbrlttybce.so] 
[File list, lib, brltty, libbrlttybec.so] 
[File list, lib, brltty, libbrlttybeu.so] 
... 

也許在我的鼻子下面有一些東西我錯過了。這可能是一個愚蠢的錯誤。有任何想法嗎?這是我在大學的最後一年項目,請幫助!

回答

2

的錯誤是最有可能在你的TreeModelisLeaf(Object node)方法。
看那TreeModel.isLeaf(Object node)的Javadoc:

返回true如果node是葉。這是可能的這個方法返回false 即使node沒有孩子。文件系統中的目錄(例如 )可能不包含任何文件;表示該目錄的節點不是葉, 但它也沒有子節點。

所以,在一個目錄(甚至目錄)的情況下,你需要返回false而不是true

+0

謝謝!我所要做的只是在isLeaf()中添加另一個條件來檢查空文件夾,它工作正常!非常感謝!!!! –