Hallo,
Ich suche einen Tip, eine Ordnerstruktur mit Unterordnern und Dateien in einer Baumstruktur wiederzugeben.
Funktionen wie Umbenennen, Kopieren, Löschen sollten mit diesem Objekt schnell und sicher zu erledigen sein.
Ich dachte an ein in sich verschachteltes Dictionary oder an ein Dictionary in dem jeder Pfad als Schlüssel abgespeichert wird.
Habt ihr bessere Ideen? Ich wäre dankbar für Anregungen!
Baumstruktur
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
An etwas änliches arbeite ich auch. Eine Backup-Datenbank...
Die Daten einer CD speichere ich in zwei Listen...
Eine für Verzeichnisse und eine für Dateien.
Jedes Verzeichniss und jede Datei bekommt eine ID...
Bei jedem Verzeichniss ist die ID des Parent-Verz. angegeben. Bei jeder Datei die ID des Verz. in dem die Datei liegt...
Aufbau der Verz.-Liste:
Aufbau der Datei-Liste:
Anmerkungen:
Weiß allerdings nicht, ob ich die Datenstruktur beibehalte... Denn diese ist zwar ideal für eine normale Datenbank, aber vielleicht nutze ich leiber eine OODB s. http://python.sandtner.org/viewtopic.php?t=2412
Die Daten einer CD speichere ich in zwei Listen...
Eine für Verzeichnisse und eine für Dateien.
Jedes Verzeichniss und jede Datei bekommt eine ID...
Bei jedem Verzeichniss ist die ID des Parent-Verz. angegeben. Bei jeder Datei die ID des Verz. in dem die Datei liegt...
Aufbau der Verz.-Liste:
Code: Alles auswählen
0 - ID
1 - parent
2 - name
3 - size
4 - description
5 - attrib
6 - createdate
7 - lastdate
8 - moddate
9 - depth
Code: Alles auswählen
0 - ID
1 - parent
2 - name
3 - size
4 - description
5 - attrib
6 - createdate
7 - lastdate
8 - moddate
9 - depth
Die ID wird für jeder Verz. und jede Datei um eins erhöht und gilt dabei als ID für
Verz. und Dateien gleichzeitig.
Bsp.:
ID | Verz.+Dateien
0 | \
1 | |--UnterVerz\
2 | |- Datei1.txt
3 | `- Datei2.txt
depth
-----
Bei Verz. gilt für das ROOT-Verzeichnis und die ersten UnterVerz. (also die Verz. im ROOT, ohne deren UnterVerz.) beide "depth = 0".
Erst das UnterVerz. eines UnterVerz. des ROOT erhält "depth = 1"
Bsp.:
depth | Verz.Struktur
0 | \ <- (Root-Verz.)
0 | |--UnterVerz1\
1 | `--UnterVerz2\
Für Dateien gilt dagegen die Regel "depth = Anzahl der Verz.". Also haben Dateien im ROOT-Verz. "depth = 0", Dateien im ersten
UnterVerz. (UnterVerz1\*.*) "depth = 1", Dateien im zweiten UnterVerz. (UnterVerz1\UnterVerz2\*.*) gilt "depth = 2" usw.
Weiß allerdings nicht, ob ich die Datenstruktur beibehalte... Denn diese ist zwar ideal für eine normale Datenbank, aber vielleicht nutze ich leiber eine OODB s. http://python.sandtner.org/viewtopic.php?t=2412
Hi Jens,
Also so ganz blicke ich da nicht durch. Ich welchem Zusammenhang stehen die einzelnen Listen zueinander? Sind sie in einem Dictionary abgespeichert? Und wie greifst du auf die Informationen der Dateien oder Ordner zu wenn du nur die Pfadangabe hast?
Also so ganz blicke ich da nicht durch. Ich welchem Zusammenhang stehen die einzelnen Listen zueinander? Sind sie in einem Dictionary abgespeichert? Und wie greifst du auf die Informationen der Dateien oder Ordner zu wenn du nur die Pfadangabe hast?
Gruß, Harry
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Nein, ich habe eine Klasse, in dem diese beiden Listen über Funktionen befüllt und abgefragt werden können...
Ich weiß nicht ob du damit was anfangen kannst, aber hier mal mein Stand der Dinge:
Das ganze ist noch wirklich Pre-Beta
z.B. ist die Funktion MakeDirInfoComplete nicht wirklich fertig...
Jetzt nutze ich os.path.walk(), aber einfachere ist os.walk()...
Es ist also noch viel zu tun...
Außerdem ist dort auch verweise zu FileVersionInfo und REGinfo... Aber die kannst du vielleicht einfach ausklammern...
Mir ist auch aufgefallen, das ich im Prinzip einige Sachen direkt in eine DB schreiben und "bearbeiten" könnte... Denn irgendwie baue ich damit fast eine kleine DB selber... Aber da ich mich noch nicht auf eine bestimmten DB festgelegt hab, kann ich z.Z. nicht recht weiter machen...
Ich weiß nicht ob du damit was anfangen kannst, aber hier mal mein Stand der Dinge:
Code: Alles auswählen
#!/usr/bin/python
# -*- coding: cp1252 -*-
__version__="0.0.3"
import os.path, time, sys
# Damit "Unterroutinen" gefunden werden, wird der Pfad erweitert:
sys.path.append("Routinen")
import FileVersionInfo
import REGinfo
class DiscData:
"""
=====================
DirInfo - Type:List
=====================
Jeder Verzeichnis ist ein Eintrag als Liste mit folgenden Informationen:
0 - ID ('NUMBER', 11, 10, 0, 0, 1) PathWalkID - Nummer auch für Dateien!
1 - parent ('NUMBER', 11, 10, 0, 0, 1) ID-Nr. des nächst höheren Verzeichnisses
2 - name ('STRING', 255, 255, 0, 0, 1)
3 - size ('NUMBER', 11, 10, 0, 0, 1)
4 - description ('STRING', 255, 255, 0, 0, 1)
5 - attrib ('STRING', 10, 10, 0, 0, 1)
6 - createdate ('DATE', 19, 19, 0, 0, 1)
7 - lastdate ('DATE', 19, 19, 0, 0, 1)
8 - moddate ('DATE', 19, 19, 0, 0, 1)
9 - depth ('NUMBER', 6, 5, 0, 0, 1)
Bsp (zwei Einträge):
(1, 0, 'R:', 576814470, None, 'D', <DbiDate object at 0x008AE060>, <DbiDate object at 0x008AE050>, <DbiDate object at 0x008AE070>, 0)
(18, 1, 'IE5', 79407911, None, 'DR', <DbiDate object at 0x008AE080>, <DbiDate object at 0x008AE090>, <DbiDate object at 0x008AE0A0>, 0)
======================
FileInfo - Type:List
======================
Jede Datei ist ein Eintrag in Form einer Liste mit folgenden Informationen:
0 - ID ('NUMBER', 11, 10, 0, 0, 1) PathWalkID, Nummer auch für Verzeichnisse!
1 - parent ('NUMBER', 11, 10, 0, 0, 1) ID-Nr. des Verz. in dem die Datei liegt!
2 - name ('STRING', 255, 255, 0, 0, 1)
3 - size ('NUMBER', 11, 10, 0, 0, 1)
4 - description ('STRING', 255, 255, 0, 0, 1)
5 - attrib ('STRING', 10, 10, 0, 0, 1)
6 - createdate ('DATE', 19, 19, 0, 0, 1)
7 - lastdate ('DATE', 19, 19, 0, 0, 1)
8 - moddate ('DATE', 19, 19, 0, 0, 1)
9 - depth ('NUMBER', 6, 5, 0, 0, 1)
Bsp (zwei Einträge):
(3, 1, 'AUTORUN.INF', 1838, None, 'R', <DbiDate object at 0x008AE060>, <DbiDate object at 0x008AE050>, <DbiDate object at 0x008AE070>, 0)
(4, 1, 'DATA1.MSI', 2348544, None, 'R', <DbiDate object at 0x008AE080>, <DbiDate object at 0x008AE090>, <DbiDate object at 0x008AE0A0>, 0)
*************
Anmerkungen
*************
PathWalkID
----------
Die ID wird für jeder Verz. und jede Datei um eins erhöht und gilt dabei als ID für
Verz. und Dateien gleichzeitig.
Bsp.:
ID | Verz.+Dateien
0 | \
1 | |--UnterVerz\
2 | |- Datei1.txt
3 | `- Datei2.txt
depth
-----
Bei Verz. gilt für das ROOT-Verzeichnis und die ersten UnterVerz. (also die Verz. im ROOT, ohne deren UnterVerz.) beide "depth = 0".
Erst das UnterVerz. eines UnterVerz. des ROOT erhält "depth = 1"
Bsp.:
depth | Verz.Struktur
0 | \ <- (Root-Verz.)
0 | |--UnterVerz1\
1 | `--UnterVerz2\
Für Dateien gilt dagegen die Regel "depth = Anzahl der Verz.". Also haben Dateien im ROOT-Verz. "depth = 0", Dateien im ersten
UnterVerz. (UnterVerz1\*.*) "depth = 1", Dateien im zweiten UnterVerz. (UnterVerz1\UnterVerz2\*.*) gilt "depth = 2" usw.
"""
def __init__( self ):
self.Disc = []
self.MyFileTypeInfo = REGinfo.FileTypeInfo()
###
### Funktionen zum hinzufügen von Daten
###
def newDisc( self, ID ):
self.Disc.append( ID )
self.currentDisc = ID
# Liste für die Verzeichniss-Informationen
self.DirInfo = []
self.currentVerzID = 0
# Liste der Datei-Daten
self.FileInfo = []
# Informationen zum Dateityp, Verknüpfung mit Programmen
self.ExtInfo = {}
def newDirectory( self, PathWalkID, DirName, DirStat ):
# Aktuelles Verz.ID für Dateien speichern, damit die Datei-Funktion auch weiß, aus
# welchem Verz. die Dateien stammen
self.currentVerzID = PathWalkID
# Pfad aufsplitten in Laufwerk und Verz.
DriveLetter, DirName = os.path.splitdrive( DirName )
if DirName == "": ### Aktuelles Verzeichnis ist das Hauptverzeichniss
# Laufwerk = Root-Verz als ersten Eintrag in der DirInfo eintragen
ParentDirID = 0
currentDirName = DriveLetter
self.DirDepth = 0
else: ### Normales Verzeichnis
# Liste erstellen mit allen Verzeichnissen
# Bsp.: ['r:', 'Verz', 'UnterVerz']
DirList = [DriveLetter] + DirName.split(os.sep)
currentDirName = DirList[-1]
# Verzeichnis Tiefe: Root + erstes Unterverz = 0
# auch genutzt für Dateien!
self.DirDepth = len(DirList) - 2
# vorletzte Verzeichniss ist das Parent-Verz.
ParentDirName = DirList[-2]
# Hohlt ID des Parent-Verz.
ParentDirID = self.getDirIDbyName( ParentDirName )
CreationTime = DirStat.st_ctime
LastAccess = DirStat.st_atime
LastModification = DirStat.st_mtime
# Stellt den Eintrag für das aktuelle Verzeichniss zusammen
Info = [
PathWalkID, # 0 - ID
ParentDirID, # 1 - parent
currentDirName, # 2 - name
0, # 3 - size
"", # 4 - description
"", # 5 - attrib
CreationTime, # 6 - createdate
LastAccess, # 7 - lastdate
LastModification, # 8 - moddate
self.DirDepth # 9 - depth
]
if ParentDirID == 0: ### Root-Verzeichnis
# Damit die "FileDepth" für Dateien im Root-Verzeichniss stimmt, wird
# self.DirDepth manipuliert
self.DirDepth = -1
self.DirInfo.append( Info )
def newFile( self, PathWalkID, FileName, FileStat ):
"""
Eine neue Datei aufnehmen
Die ID der Datei ist die PathWalkID, die auch glaichzeitig für Verzeichnisse ist, aber nicht für
den Zusammenhang zwischen Verzeichnis <-> Datei!!! Dafür ist die "parent"-ID zuständig!!! Sie
gibt die ID-Nr. des Verzeichnisses an, in dem die Datei liegt.
"""
# ID zur verknpüpfung zwischen Datei <-> Endungs-Information
ExtInfoID = self.newExtInfo( FileName )
self.FileInfo.append(
{
"ID" : PathWalkID,
"parent" : self.currentVerzID,
"name" : FileName,
"size" : FileStat.st_size, # FileSize
"description" : "",
"attrib" : "",
"createdate" : FileStat.st_ctime, # CreationTime
"lastdate" : FileStat.st_atime, # LastAccess
"moddate" : FileStat.st_mtime, # LastModification
"depth" : self.DirDepth + 1, # FileDepth
"extInfoID" : ExtInfoID
}
)
def newExtInfo( self, FileName ):
"""
wird von self.newFile() aufgerufen!
DateiTyp Informationen über Verknüpfung und Programm-Versionen
benötigt Modul: REGinfo und FileVersionInfo
0 - Ext Dateiendung
1 - TypeInfo Allgemeine Beschreibung des DateiTyps
2 - Program Programm mit dem der DateiTyp verknüpft ist
3 - CompanyName |-- Firma
4 - FileDescription |--
5 - FileVersion |-- Version
6 - LegalCopyright `-- Copyright
self.ExtInfo
"""
FileExt = os.path.splitext( FileName )[1]
if FileExt == "": return -1
if self.ExtInfo.has_key(FileExt):
return self.ExtInfo[FileExt]["ID"]
ExtInfo = self.MyFileTypeInfo.getInfo( FileExt )
#~ "Type" - DateiTyp-Kennung (wie Win-Befehl "assoc" herrausliefert)
#~ "TypeInfo" - Allgemeine Beschreibung des DateiTyps
#~ "Program" - direkter Pfad zur Datei (sofern existiert)
if ExtInfo != None:#and ExtInfo.has_key("Program"):
print FileExt, ExtInfo
DescItems = ["CompanyName", "FileDescription", "FileVersion", "LegalCopyright"]
FileInfo = FileVersionInfo.getFileVerInfo( ExtInfo["Program"], DescItems )
if FileInfo:
for i in FileInfo:
print i,"-", FileInfo[i]
else:
print "- Keine DateiInformation vorhanden -"
print
#~ self.ExtInfo
#~ print Ext
###
### allgemeine Funktionen zum Auslesen der Daten, die nicht
### konkreten Problemlösungen sind
def getItemsByItem( self, List, SearchNr, SearchValue, SourceNr ):
"""
Liefert eine Liste aller Werte in der >SourceNr<-Spalte, wenn in
der >SearchNr<-Spalte der Wert = >SearchValue< ist.
Das ganze wird in der >List< durchgeführt.
Bsp.
| 0 | 1 | 2
----------------
0 | A1 | B1 | C1
1 | A2 | B1 | C2
2 | A3 | B1 | C3
getItemsByItem( XXX, 0, "A2", 2) => ["C2"]
getItemsByItem( XXX, 1, "B1", 1) => ["A1","A2","A3"]
"""
Results = []
for i in List:
if i[SearchNr] == SearchValue:
Results.append( i[SourceNr] )
return Results
def getItemByItem( self, List, SearchNr, SearchValue, SourceNr ):
"""
Im Prinzip die gleiche Funktion wie getItemsByItem()!
Jedoch wird beim ersten Treffer abgebrochen.
"""
for i in List:
if i[SearchNr] == SearchValue:
return i[SourceNr]
###
### Funktionen zum auslesen der Daten
###
def getVerzFromIDlist( self, DirIDlist ):
"""
Liefert eine Liste der VerzNamen von der >DirIDlist< zurück.
Wird bei fullPath() verwendet.
"""
DirList = []
for DirID in DirIDlist:
DirList.append( getItemByItem( self.DirInfo, 1, DirID, 2) )
print "DirList:",DirList
return DirList
def getFilesByDirID( self, DirID ):
"""
Liefert eine Liste aller Datei-IDs zurück, die in dem Verzeichnis mit dem
>DirID< sind, zurück.
"""
return self.getItemListByItemValue( self.FileInfo, "ID", DirID, "parent" )
def getDirIDbyName( self, DirName ):
"""
Liefert die ID des ersten Verz. mit dem Namen >DirName< zurück
Wird z.B. von newDirectory() benötigt
"""
for i in self.DirInfo:
currentDirName = i[2]
if currentDirName == DirName:
return i[0]
print ">Fehler! [%s] nicht gefunden!" % DirName
def getfullPathByDirID( self, DirID ):
"""
Liefert den kompletten Pfad eines Verzeichnisses zurück, in dem
die Parent-Verkettung vollständig aufgelöst wird.
"""
PathIDs = []
while 1:
PathIDs.append( DirID )
# DirID des Parent-Verzeichnisses:
DirID = self.getItemByItem( self.DirInfo, 1, DirID, 0 )
if ID==0: break
# ID-Liste umkehren
PathIDs.reverse()
VerzListe = self.getVerzFromIDlist( PathIDs )
print "\\".join(VerzListe)
###
### Hilfsfunktionen
###
def getMaxDirDepth( self ):
"""
Liefert den höchsten "depth"-Wert für Verz. zurück
Wird von MakeDirInfoComplete() gebraucht
"""
MaxDirDepth = 0
for i in self.DirInfo:
if i[9]>MaxDirDepth:
MaxDirDepth = i[9]
return MaxDirDepth
def MakeDirInfoComplete( self ):
"""
Addiert alle Dateigrößen
"""
print "="*79
for i in self.DirInfo[::-1]:
print ">",i[2]
DirID = i[0]
print DirID
# BytesListe, jeder Datei in dem aktuellen Verzeichniss:
BytesList = self.getItemListByItemValue( self.FileInfo, "size", DirID, "parent" )
AllBytes = 0
for Bytes in BytesList:
AllBytes += Bytes
print AllBytes
print self.getFilesByDirID( DirID )
print "--XXX"
def getItemListByItemValue( self, Liste, getKey, filterValue, filterKey ):
"""
Gibt eine gefilterte Liste aus einer >Liste<, die ein Dict beinhaltet, zurück.
Bsp "Liste":
L=[
{ "item1":"1" , "item2":"2" }
{ "item1":"10" , "item2":"20" }
{ "item1":"100", "item2":"200" }
{ "item1":"33" , "item2":"20" }
]
getItemListByItemValue(
Liste = L,
getKey = "item1",
filterValue = "20"
filterKey = "item2"
)
Ergebnis-Liste:
[ "10", "33" ]
"""
result = []
for i in Liste:
if i[filterKey] == filterValue:
result.append( i[getKey] )
return result
###
### Debug-Funktionen:
###
def dumpDirData( self ):
print "-"*79
print "Disc:",self.Disc
for i in self.DirInfo:
print i
print "-"*79
def dumpFileData( self ):
print "-"*79
print "Disc:",self.Disc
for i in self.FileInfo:
print i, self.FileInfo[i]
print "-"*79
def getDiscID( DriveLetter ):
from os import popen
shell = popen( "dir %s:" % DriveLetter )
DiscID = shell.readlines()[1].split(":")[1].strip()
shell.close()
DiscID = DiscID[:4]+DiscID[5:] # MittelStrich entfernen
return DiscID
def GetData( PathWalkID, dirname, FileNameList ):
if PathWalkID[0]>100: return
PathWalkID[0] += 1
print ">",PathWalkID[0],dirname
DirStat = os.stat( dirname+"\\" )
MyDiscData.newDirectory( PathWalkID[0], dirname, DirStat )
for FileName in FileNameList:
CompleteFilePath = dirname+os.sep+FileName
if os.path.isfile( CompleteFilePath ):
#~ print CompleteFilePath
PathWalkID[0] += 1
FileStat = os.stat( CompleteFilePath )
MyDiscData.newFile( PathWalkID[0], FileName, FileStat )
#~ time.strftime("%d.%m.%Y - %H:%M:%S",time.localtime(Datum))
MyDiscData = DiscData()
DriveLetter = "r"
DiscID = getDiscID( DriveLetter )
MyDiscData.newDisc( DiscID )
DiscPath = DriveLetter+":"
PathWalkID = [0]
os.path.walk( DiscPath, GetData, PathWalkID)
#~ MyDiscData.dumpFileData()
MyDiscData.MakeDirInfoComplete()
#~ MyDiscData.dumpDirData()

Jetzt nutze ich os.path.walk(), aber einfachere ist os.walk()...
Es ist also noch viel zu tun...
Außerdem ist dort auch verweise zu FileVersionInfo und REGinfo... Aber die kannst du vielleicht einfach ausklammern...
Mir ist auch aufgefallen, das ich im Prinzip einige Sachen direkt in eine DB schreiben und "bearbeiten" könnte... Denn irgendwie baue ich damit fast eine kleine DB selber... Aber da ich mich noch nicht auf eine bestimmten DB festgelegt hab, kann ich z.Z. nicht recht weiter machen...
-
- Python-Forum Veteran
- Beiträge: 2010
- Registriert: Freitag 11. Oktober 2002, 18:00
- Wohnort: Salzburg
- Kontaktdaten:
Hi HarryH,
das ist so eine Aufgabenstellung, die so richtig nach OOP schreit
Ich umreisse mal grob, wie ich das lösen würde.
1. Eine Basisklasse 'Node' erstellen. Diese bekommt als Attribute den Namen und den Parent, und die Methoden zum umbenennen, kopieren und löschen.
2. Davon eine Klasse 'Folder' ableiten, zum einfachen implementieren von Dictionaryfunktionalität kann die Klasse Folder auch gleichzeitig von dict abgeleitet sein.
3. Noch eine Klasse 'Entry' die dann die Daten enthält, auch abgeleitet von 'Node'.
4. Von 'Folder' würde ich auch noch eine Klasse 'Root' ableiten, in der die Funktionen zum löschen und umbenennen deaktiviert werden.
Beim Umbenennen muss dann in der Methode von Node einfach der Name von der Node-Instanz geändert und im Parent der entsprechenden Eintrag gelöscht und mit dem neuen Namen neu eingefügt werden. Was durch das Attribut Parent geschehen kann. Auch kann '__getitem__' in Folder so geändert werden, daß auch Pfade übergeben werden können und diese recursiv aufgelöst werden.
Gruß
Dookie
das ist so eine Aufgabenstellung, die so richtig nach OOP schreit

Ich umreisse mal grob, wie ich das lösen würde.
1. Eine Basisklasse 'Node' erstellen. Diese bekommt als Attribute den Namen und den Parent, und die Methoden zum umbenennen, kopieren und löschen.
2. Davon eine Klasse 'Folder' ableiten, zum einfachen implementieren von Dictionaryfunktionalität kann die Klasse Folder auch gleichzeitig von dict abgeleitet sein.
3. Noch eine Klasse 'Entry' die dann die Daten enthält, auch abgeleitet von 'Node'.
4. Von 'Folder' würde ich auch noch eine Klasse 'Root' ableiten, in der die Funktionen zum löschen und umbenennen deaktiviert werden.
Beim Umbenennen muss dann in der Methode von Node einfach der Name von der Node-Instanz geändert und im Parent der entsprechenden Eintrag gelöscht und mit dem neuen Namen neu eingefügt werden. Was durch das Attribut Parent geschehen kann. Auch kann '__getitem__' in Folder so geändert werden, daß auch Pfade übergeben werden können und diese recursiv aufgelöst werden.
Gruß
Dookie
[code]#!/usr/bin/env python
import this[/code]
import this[/code]
Hallo,
Hier mal ein Code, in dem die Treestructur in einem verschachtelten Dictionary aufgebaut ist.
Meldet euch bitte ob der Ansatz richtig ist und wenn Fehler gefunden werden.
Die Daten werden folgendermaßen gesetzt:
Hier mal ein Code, in dem die Treestructur in einem verschachtelten Dictionary aufgebaut ist.
Meldet euch bitte ob der Ansatz richtig ist und wenn Fehler gefunden werden.
Code: Alles auswählen
import os
import copy
class Dict_Tree:
def __init__(self, d = {}):
"""
d = Dicionary, that will representing the treestructur
"""
self.dict_obj = d
self.folder_id = 1
self.file_id = 2
def GetFolderData(self, path):
"""
Get data from the folderpath
path = list or tuple with items or path
"""
dic = self.__GetData(path)
if dic:
if self.folder_id in dic:
return dic[self.folder_id]
def GetFileData(self, path):
"""
Get data from the filepath
path = list or tuple with items or path
"""
dic = self.__GetData(path)
if dic:
if self.file_id in dic:
return dic[self.file_id]
def GetPathFolders(self, path):
"""
Get all underroots from the path, when it is a dictionary
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.__GetData(path)
if dic and type(dic) == dict:
folderlist = []
for i in dic:
if type(dic[i]) == dict and not self.file_id in dic[i]:
folderlist.append(i)
return folderlist
else:
return []
def GetPathFiles(self, path):
"""
Get all files from the path, when it is a dictionary
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.__GetData(path)
if dic and type(dic) == dict:
filelist = []
for i in dic:
if type(dic[i]) == dict and self.file_id in dic[i]:
filelist.append(i)
return filelist
else:
return []
def SetFolderData(self, path, data = None):
"""
Set data for the folder
path = list or tuple with items or path that will be set
data = The data to set for the folder
"""
path = self.ConvertPathToItemlist(path) + [self.folder_id]
return self.__SetData(path, data)
def SetFileData(self, path, data = None):
"""
Set data for the file
path = list or tuple with items or path that will be set
data = The data to set for the file
"""
path = self.ConvertPathToItemlist(path) + [self.file_id]
return self.__SetData(path, data)
#***************#
#Privat methods #
#***************#
def __GetData(self, path):
"""
Get the data from the path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
if self.ExistPath(path):
dic = self.dict_obj
for key in path:
dic = dic[key]
return dic
def __SetData(self, path, data = None):
"""
Set a path and her data or overwrite an existing pathdata
path = list or tuple with items or path that will be set
data = data for the path. It can be every object
"""
path = self.ConvertPathToItemlist(path)
if path:
dic = self.dict_obj
for key in path[:-1]:
dic.setdefault(key, {})
dic = dic[key]
if path[-1] in dic and type(data) == dict:
dic[path[-1]].update(data)
return True
else:
dic[path[-1]] = data
return True
#*************#
#Test methods #
#*************#
def ExistPath(self, path):
"""
Test the existence from the path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.dict_obj
test = True
for key in path:
if type(dic) == dict and key in dic:
dic = dic[key]
else:
test = False
break
return test
def ConvertPathToItemlist(self, path):
"""
Convert path to Itemlist
path = list or tuple with items or path
"""
if type(path) == str:
if os.sep != "/":
path = path.replace(os.sep, "/").strip("/")
return path.split("/")
elif type(path) == list:
return path
elif type(path) == tuple:
return list(path)
else:
raise TypeError, 'Requires list, tuple or string'
#*****************#
# Spezial methods #
#*****************#
def RenamePath(self, path, newpath):
"""
Rename a path
path = list or tuple with items or path that will be rename
newpath = New name for the path. It can be a list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
newpath = self.ConvertPathToItemlist(newpath)
if self.ExistPath(path) and path and newpath and path != newpath:
dic = self.dict_obj
for key in path[:-1]:
dic = dic[key]
old = dic.pop(path[-1])
self.__SetData(newpath, old)
return True
def CutPath(self, path, newpath = None):
"""
Cut a path
path = list or tuple with items or path that will be cut
newpath = list or tuple with items or path that will be insert the cutpath
"""
path = self.ConvertPathToItemlist(path)
if self.ExistPath(path) and path != newpath:
if newpath:
newpath = self.ConvertPathToItemlist(newpath)
return self.RenamePath(path, newpath)
else:
return self.__GetData(path)
def CopyPath(self, path, newpath = None):
"""
Copy a path
path = list or tuple with items or path that will be copy
newpath = list or tuple with items or path that will be insert the copypath
"""
path = self.ConvertPathToItemlist(path)
if self.ExistPath(path) and path != newpath:
if newpath:
newpath = self.ConvertPathToItemlist(newpath)
return self.__SetData(newpath, copy.deepcopy(self.__GetData(path)))
else:
return copy.deepcopy(self.__GetData(path))
def InsertPath(self, insertpath, data):
"""
Insert data in path
insertpath = list or tuple with items or path
data = The data to insert in the insertpath
"""
return self.__SetData(insertpath, data)
def DelPath(self, path):
"""
Delete a path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
if self.ExistPath(path) and path:
dic = self.dict_obj
for key in path[:-1]:
dic = dic[key]
del dic[path[-1]]
return True
Code: Alles auswählen
folderlist = [...]
filelist = [...]
tree = Dict_Tree()
for i in folderlist:
tree.SetFolderData(i)
for i in filelist:
tree.SetFileData(i)
Gruß, Harry
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Code: Alles auswählen
def ExistPath(self, path):
"""
Test the existence from the path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.dict_obj
test = True
for key in path:
if type(dic) == dict and key in dic:
dic = dic[key]
else:
test = False
break
return test
Code: Alles auswählen
def ExistPath(self, path):
"""
Test the existence from the path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.dict_obj
test = True
for key in path:
if type(dic) == dict and key in dic:
dic = dic[key]
else:
return False
Außerdem wie ist folderlist und filelist Aufgebaut? Ich meine, wo entsteht die beziehung zwischen den Beiden, also in welchen Verz. eine Datei liegt usw.
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Ach das hab ich garnicht gesehen, aber was ist mit dem:
So hat man sich die test-Variable eingespart
Code: Alles auswählen
def ExistPath(self, path):
"""
Test the existence from the path
path = list or tuple with items or path
"""
path = self.ConvertPathToItemlist(path)
dic = self.dict_obj
for key in path:
if type(dic) == dict and key in dic:
dic = dic[key]
else:
return False
return True
Hallo,
Ich habe selbst auch noch einen Fehler entdeckt.
Neuer Code:
Zu der letzten Frage von Jens:
Filelist und Folderlist werden durch self.folder_id und self.file_id voneinandner unterschieden. Existiert weder die eine noch die andere in einem "Verzeichnis" wird das Objekt als Folder erkannt.
Die self.folder_id und self.file_id sind gleichzeitig die Schlüssel für die Daten zu dem jeweiligen Folder- oder File-Objekt.
Ich habe selbst auch noch einen Fehler entdeckt.
Neuer Code:
Code: Alles auswählen
def ConvertPathToItemlist(self, path):
"""
Convert path to Itemlist
path = list or tuple with items or path
"""
if type(path) == str:
if os.sep != "/":
path = path.replace(os.sep, "/")
path = path.strip("/")
if path:
return path.split("/")
else:
return []
elif type(path) == list:
return path
elif type(path) == tuple:
return list(path)
else:
raise TypeError, 'Requires list, tuple or string'
Filelist und Folderlist werden durch self.folder_id und self.file_id voneinandner unterschieden. Existiert weder die eine noch die andere in einem "Verzeichnis" wird das Objekt als Folder erkannt.
Die self.folder_id und self.file_id sind gleichzeitig die Schlüssel für die Daten zu dem jeweiligen Folder- oder File-Objekt.
Gruß, Harry
- jens
- Python-Forum Veteran
- Beiträge: 8502
- Registriert: Dienstag 10. August 2004, 09:40
- Wohnort: duisburg
- Kontaktdaten:
Was ich ehr meinte, wie sieht die Datenstruktur aus... Du wolltest doch "Ordnerstruktur mit Unterordnern und Dateien in einer Baumstruktur" festhalten...
Wenn man jetzt deine Klasse mit den Daten von os.walk() füllen will, wie geht das?
Einfach so:
EDIT: Hab gerade gesehen, so ist's wohl gedacht... Und wie bekomme ich die Daten wieder herraus?
Wenn man jetzt deine Klasse mit den Daten von os.walk() füllen will, wie geht das?
Einfach so:
Code: Alles auswählen
tree = Dict_Tree()
for root, folderlist, filelist in os.walk(pfad):
for i in folderlist:
tree.SetFolderData(i)
for i in filelist:
tree.SetFileData(i)
Hi,
Nein es geht so:
Über die Methoden SetFolderData und SetFileData könnte man dann noch jedem Objekt einen Datensatz zuordnen, evtl. auch über zusätzliche Methoden.
Edit (Leonidas): Code in Python Tags gesetzt, ist so lesbarer.
Nein es geht so:
Code: Alles auswählen
folder = r"D:\Python"
tree = Dict_Tree()
for root, dirs, files in os.walk(folder):
#search files
for file in files:
file = os.path.join(root, file)
tree.SetFileData(file)
#search folder
for dir in dirs:
dir = os.path.join(root, dir)
tree.SetFolderData(dir)
#Folder-Liste anzeigen
print tree.GetPathFolders("D:\Python")
#File-Liste anzeigen
print tree.GetPathFiles("D:\Python")
#Umbenennen
tree.RenamePath("D:\Python", "C:\Python")
#Foldender Pfad existiert nicht mehr, da umbenannt
print tree.GetPathFolders("D:\Python")
#Nun geht es
print tree.GetPathFolders("C:\Python")
Edit (Leonidas): Code in Python Tags gesetzt, ist so lesbarer.
Gruß, Harry
Meine Variante hat den Vorteil das ich fast direkt auf einen Pfad zugreifen kann. Ich muss nicht alle Elemente über Schleifen durchlaufen um die Daten zu einem File oder einem Ordner zu erhalten.
Darüber hinaus kann ich jedem "Pfad-Objekt" beliebige Daten zuordnen(dictionarys, listen ...).
Außerdem bin ich nicht nur an Filesystem-Strukturen gebunden. Ich kann auch andere Tree-Strukturen erzeugen, die keine Verbindung zum Filesystem besitzten. Deswegen kann man auch eine Liste oder eine Tuple als 'path' übergeben.
Darüber hinaus kann ich jedem "Pfad-Objekt" beliebige Daten zuordnen(dictionarys, listen ...).
Außerdem bin ich nicht nur an Filesystem-Strukturen gebunden. Ich kann auch andere Tree-Strukturen erzeugen, die keine Verbindung zum Filesystem besitzten. Deswegen kann man auch eine Liste oder eine Tuple als 'path' übergeben.
Gruß, Harry