sawMedlem sedan mars 20011 880 inlägg Jag försöker att göra en "utforskare" men stött på en del problem.
//här tar jag fram de logiska drivarna och för varje driver vill jag ha
alla mappar i varje driver
private void initTreeNode()
{
try
{
foreach (string s in Environment.GetLogicalDrives())
{
try
{
TreeNode node = treeView1.Nodes.Add(s);
GetFolders(s, node.Nodes);
}
catch (Exception fel)
{
label1.Text = fel.Message + " " + s;
}
}
}
catch (Exception fel)
{
label1.Text = fel.Message;
}
}
private void GetFolders(string path, TreeNodeCollection nodes)
{
string[] dirs = Directory.GetDirectories(path);
foreach (string p in dirs)
{
string dp = p.Substring(path.Length);
nodes.Add(p.Substring(path.Length));
}
//// add nodes for all files in this directory (folder)
string[] files = Directory.GetFiles(path, "*.*");
foreach (string p in files)
{
nodes.Add(p, p.Substring(path.Length));
}
//// add all subdirectories for each directory (recursive)
for (int i = 0; i < nodes.Count; i++)
{
GetFolders(dirs[i] + "\\", nodes[i].Nodes);
}
}
Problem:
De enda undermappar som den hittar (förutom de i A:\) är $RECYCLE.BIN.
Är min kod kanske inte tillräkligt optimerad?
Hur bör jag istället skriva?
sawMedlem sedan mars 20011 880 inlägg Nu har jag löst det i stort sett, men jag måste nog ha byggt det lite tokigt
för det tar en bra stund innan applikationen ritas upp.
private void initTreeNode()
{
DirectoryInfo modermapp;
DirectoryInfo[] undermapparIModermapp;
try
{
foreach (string s in Environment.GetLogicalDrives())
{
try
{
Application.DoEvents();
TreeNode node = treeView1.Nodes.Add(s);
modermapp = new DirectoryInfo(s);
undermapparIModermapp = modermapp.GetDirectories();
////treeView1.ImageIndex = 1;
Application.DoEvents();
AddSubdirectories(modermapp, node);
}
catch (Exception fel)
{
label1.Text = fel.Message + " " + s;
}
}
}
catch (Exception fel)
{
label1.Text = fel.Message;
}
}
private void AddSubdirectories(DirectoryInfo dir, TreeNode node)
{
foreach(DirectoryInfo subdir in dir.GetDirectories())
{
Application.DoEvents();
if (subdir.Name == "$AVG8.VAULT$" || subdir.Name == "$RECYCLE.BIN" || subdir.Name == "RECYCLER")
{ }
else
{
Application.DoEvents();
TreeNode child = node.Nodes.Add(subdir.Name);
AddSubdirectories(subdir, child);
}
}
}
Ett annat problem är att den vill inte visa någonting i C:\, men det kan väll
bero på att jag kör Vista???
cokMedlem sedan dec. 2005664 inlägg Har inte kollat din kod men att det tar tid kan vara listningen av enheterna som du gör med "Environment.GetLogicalDrives()", inte så konstigt då den kanske ska kolla nätdiskar etc.
Kolla hur lång tid det tar att köra den raden.
sawMedlem sedan mars 20011 880 inlägg Det tar ca 10 - 15 sekunder.
Jag har byggt om igen och fått det något snabbare.
public enum DriveType : int
{
Unknown = 0,
NoRoot = 1,
Removable = 2,
Localdisk = 3,
Network = 4,
CDRom = 5,
RAMDrive = 6,
Fixed=7
}
[STAThread]
[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
public static extern int GetDriveType(string lpRootPathName);
private void initTreeNode()
{
DirectoryInfo modermapp;
int driver=0;
Application.DoEvents();
string[] allaDrivers = Environment.GetLogicalDrives();
foreach (string s in allaDrivers)
{
Application.DoEvents();
if (GetDriveType(s) == (int)DriveType.CDRom)
driver = 0;
else if (GetDriveType(s) == (int)DriveType.Removable)
driver = 3;
else if (GetDriveType(s) == (int)DriveType.Fixed)
driver = 4;
try
{
TreeNode node = treeView1.Nodes.Add(s, s, driver);
modermapp = new DirectoryInfo(s);
Application.DoEvents();
AddSubdirectories(modermapp, node);
}
catch (Exception fel)
{
label1.Text = fel.Message + " " + s;
}
}
}
Kan jag optimera något?
Ett annat problem, den skifftar inte iconer, tips???
spangoMedlem sedan juni 20008 205 inlägg Rätta mig om jag har fel, men bygger du inte upp ett helt träd som motsvarar alla kataloger/filer på alla enheter? Inte så konstigt om det blir långsamt i sådana fall.
Dessutom gör du GetDriveType upp till tre gånger. Gör en switch/case på den eller spara undan resultatet i en lokal variabel istället.
sawMedlem sedan mars 20011 880 inlägg Jag har lokaliserat problemet, men jag vet inte hur jag skall lösa det...
//jag försöker med denna if-sats, men den fungerar inte.
if(GetDriveType(s) == (int)DriveType.Fixed ||GetDriveType(s) == (int)DriveType.Removable)
AddSubdirectories(modermapp, node);//detta tar tid.
GladhMedlem sedan maj 20012 812 inlägg
saw skrev:
AddSubdirectories(modermapp, node);//detta tar tid.
Det är ju inte konstigt att den tar tid, då denna metod inte bara skriver ut den mapp som du står i, utan även alla barn som finns till denna mapp och deras barn och deras barn och deras barn och deras barn... har du många mappar så tar det ju en stund...
Lösningen är att du endast lägger till mapparna när du behöver visa dem. Alltså du låter bli den rekursiva hantering som du har i AddSubdirectories, och när du trycker på en mapp, så lägger du till den mappens mappar i trälistan.
Lazy Loading helt enkelt...
- M
sawMedlem sedan mars 20011 880 inlägg Ok Gladh, jag förstår vad du säger men fasnar i alla fall.
//om jag gör så här, så går det snabbt, och då får jag fram ett plustecken
om det finns undermappar.
TreeNode node = treeView1.Nodes.Add(s, s, 4);
modermapp = new DirectoryInfo(s);
DirectoryInfo[] undermappar = modermapp.GetDirectories();
foreach (DirectoryInfo mapp in undermappar)
{
node.Nodes.Add(mapp.Name, mapp.Name, 2);
}
..men här fasnar jag, jag måste ju koppla AddSubdirectories(modermapp,
node); och jag lyckas inte med det, inte under click eller någon annan stans.
sawMedlem sedan mars 20011 880 inlägg Jag åkte ut och tömmde båten på vatten, och kom på det:
string s = node.FullPath;
modermapp = new DirectoryInfo(s);
DirectoryInfo[] undermappar = modermapp.GetDirectories();
foreach (DirectoryInfo mapp in undermappar)
{
node.Nodes.Add(mapp.Name, mapp.Name, 2);
}
Jag la denna i treeView1_AfterSelect och då fungerar den bra.
Jag återkommer vid vidare problem.