Eigene Kompremmierung

  • VB.NET

Es gibt 10 Antworten in diesem Thema. Der letzte Beitrag () ist von ~blaze~.

    Eigene Kompremmierung

    Hi, ich wollte mal was nachfragen:
    Ihr kennt doch bestimmt Archive/Massendateien wie .dat, .bar, .iso etc.
    z.B: eine 2 GB große .dat Datei von einem Spiel.
    Wie haben Sie diese Datei erstellt und ausgelesen bzw. Sie arbeiten ja mit der Datei als wäre es ein Ordner.
    Meine Frage wie kann ich so etwas "nachmachen", oder ist das überhaupt möglich in VB.Net?

    Wäre dankbar über antworten (.zip, .rar nicht schreiben, die kenne ich sind aber keine Massendateien)
    Mfg
    Nehmen wir ein Beispiel:
    - gangschta.exe (350 MB)
    - readme.txt (110 kb)
    - needdll.dll (5 MB)

    Ich muss sozusagen eine Datei namens: ".dat" erstellen mit einem Tool, aber welchen Code soll ich nutzen wenn diese Dateien unter "my.computer.filesystem.currentdirectory & "\togeneratedfile" liegen.
    Wie schreibe ich Sie nun unter "my.computer.filesystem.currentidrectory & "\data.dat".
    Und wie lese ich Sie aus?

    Mfg
    Was ist denn so schlimm an Zip? Viele Spiele (z. B. BF2, CoD, Crysis) nutzten es als "Massendateien", wie du es nennst. Du kannst beliebig viele Dateien in eine packen und einzeln wieder auslesen. Das ist doch genau das, was du willst? Und mit der #ziplib geht es ganz einfach.

    Viele Grüße, Phil.
    Hi
    Naja beliebig viele stimmt nicht ganz und von den Datenmengen ists eingeschränkt. Außerdem ist der Zip-Algorithmus vielleicht nicht unbedingt der richtige Kompressionsalgorithmus für die meisten Dateitypen.
    Es ist übrigens ganz einfach einen eigenen Dateitypen ohne Kompression zu entwickeln, der sowas kann:
    - Nimm einen BinaryWriter
    - Öffne einen Stream oder lese die Bytes der Eingabedatei ein
    - Schreibe die Länge des Streams bzw. der Quelldatei in den Output-Stream
    - Schreibe den relativen Dateinamen der Datei (entweder mit Null-Byte am Schluss, was normal wäre oder per System.Text.Encoding.GetBytes() und dann mit Länge davor, was ich persönlich "besser" finde, aber nicht wirklich äquivalent zum Prinzip von Strings ist, nur wird dabei halt ein Puffer konstanter Länge eingesetzt, wodurch es nicht zum vorherigen Inspizieren der Daten des Streams oder zu einer mehrfachen Pufferallokation oder einer Pufferallokation mit überschüssigem Speicherplatz kommt)
    - Schreibe den Inhalt der Datei
    Und das machst du für alle Dateien. Auslesen läuft natürlich analog und die Reihenfolge ist beliebig (abgesehen vom Inhalt). Um die Suche in der Datei zu verbessern, kannst du auch im Kopf oder im Fuß der Datei (Fuß ist dynamischer und die zu erzeugende bzw. verschiebende Datenmenge ist wahrscheinlich geringer, als der Inhalt, wenn die Daten verändert werden) Informationen über die Pfade anlegen. Ich meine da zum Beispiel einen Zeiger innerhalb der Datei, der auf Daten, die einem bestimmten Pfad angehören, verweist. Wenn du die Dateien nach Dateipfad sortierst, könnte das zum Beispiel so aussehen:
    Aus den gespeicherten Dateien und Ordnern in C:\ extrahieren wir den Pfad relativ zu C:\:
    C:\Windows\x.dll
    C:\Windows\Microsoft.Net\y.dll
    C:\Windows\system\z.dll

    ==>
    Windows\x.dll
    Windows\Microsoft.Net\y.dll
    Windows\system\z.dll

    Hier kann man das "Windows" für alle Pfade extrahieren. Der Block wird damm im Fuß in der Tabelle gespeichert und per Zeiger darauf verwiesen. Außerdem wird vor dem Datenblock noch ein Block von 8 Bytes gesetzt, um auf den Pfad unten zu verweisen. Damit wird dann das "Windows" oben weggeschnitten, damit dann letztendlich der Datenblock z.B. nur noch aus sowas besteht, wie:
    - Verweis auf den Ordner
    - Zeiger auf den nächsten Datenblock
    -"x.dll"
    - Dateilänge der Datei 'C:\Windows\x.dll' (bzw. ergibt sich natürlich auch aus den anderen 3 Blöcken, könnte man also weglassen)
    - Dateiinhalt

    und der Dateifuß:
    - Zeiger auf 1. Datei aus dem Ordner
    - Anzahl der Dateien aus dem Ordner (mit Unterordner), also 3 (nat. 0, wenn der Ordner leer ist)
    - relativer Ordnerpfad, also "Windows"

    Für jede Datei kannst du natürlich noch die Attribute, Erstell-, Aufrufdaten usw. speichern.

    Gruß
    ~blaze~