AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Base64/ Mime für Dateien

Ein Thema von Capstone · begonnen am 13. Sep 2017 · letzter Beitrag vom 17. Sep 2017
Antwort Antwort
Redeemer

Registriert seit: 19. Jan 2009
Ort: Kirchlinteln (LK Verden)
1.123 Beiträge
 
Delphi 2009 Professional
 
#1

AW: Base64/ Mime für Dateien

  Alt 16. Sep 2017, 16:53
Glückwunsch. Dein Delphi ist einfach nur scheißen-langsam.

Angehängt ist ein Kompilat deines Projekts mit Delphi 2009. Ich habe nichts gemacht außer es geöffnet und F9 gedrückt, dadurch wurde das Programme einige hundert Mal schneller. Das Kompilat meines Projekts ist auch angehängt, auch wenn es nichts bringt.
Wenn du willst, ersetze mal beide WriteBuffer durch Write. Die beiden sind eigentlich identisch, aber wer weiß.

Ein mögliches Problem wäre das zu feine Reservieren von Speicher. Füge doch einfach mal vor der for-Schleife folgende Zeile ein:
Output.Size := ((Input.Size + 2) div 3) * 4; Wenn das noch immer nicht schneller geht, müsste man per Pointer in den Stream schreiben. Melde dich, ich ändere die Methode.
Angehängte Dateien
Dateityp: 7z SimpleBase64.7z (198,5 KB, 4x aufgerufen)
Janni
2005 PE, 2009 PA, XE2 PA
  Mit Zitat antworten Zitat
Redeemer

Registriert seit: 19. Jan 2009
Ort: Kirchlinteln (LK Verden)
1.123 Beiträge
 
Delphi 2009 Professional
 
#2

AW: Base64/ Mime für Dateien

  Alt 17. Sep 2017, 17:26
Die Methode von mir hatte zwei Fehler, was zu einem ungültigen Ergebnis führte. Hier die korrekte Version:
Delphi-Quellcode:
procedure Base64EncodeStream(Input, Output: TStream);
const
  Base64: array[0..64] of Byte = (
  65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,
  97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,
  48,49,50,51,52,53,54,55,56,57,43,47,$3D);
var
  count: Byte;
  temp: Cardinal;
  i, j: Integer;
begin
  Temp := 0;
  Count := 3;
  Output.Size := (Input.Size + 2) div 3 * 4;
  for i := 0 to (Input.Size + 2) div 3 - 1 do
  begin
    Count := Input.Read(temp, 3);
    temp := temp and $ff00 + temp shl 16 + temp shr 16 and $ff; // Endianness drehen (vereinfacht weil nur 3 Byte verwendet)
    for j := 0 to Count do
    begin
      Output.Write(Base64[temp shr 18 and $3f], 1);
      temp := temp shl 6;
    end;
  end;
  for j := Count to 2 do
  Output.Write(Base64[64], 1); // Schreibe ein Gleichzeichen zum Auffüllen
end;
Hier übrigens der Dekoder:
Delphi-Quellcode:
procedure Base64DecodeStream(Input, Output: TStream);
const
  Base64: array[Byte] of ShortInt = (
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,62,-1,-1,-1,63,52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-1,-1,-1,
  -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1,
  -1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,-1,-1,-1,-1,-1,
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
  -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1);
var
  count, b: Byte;
  temp: Cardinal;
  i: Integer;
begin
  Temp := 0;
  Count := 0;
  Output.Size := Trunc(Input.Size / 4 * 3); // maximal möglichen Output reservieren
  for i := 0 to Input.Size - 1 do
  begin
    Input.Read(b, 1);
    if Base64[b] > -1 then
    begin
      temp := temp shl 6 or Byte(Base64[b]);
      inc(Count);
      if Count = 4 then
      begin
        temp := temp and $ff00 + temp shl 16 + temp shr 16; // Endianness drehen (vereinfacht weil nur 3 Byte verwendet)
        Output.Write(temp, 3);
        temp := 0;
        Count := 0;
      end;
    end;
  end;
  if Count > 1 then // Rest behandeln, der kein 3er-Block ist (ein Base64-Rest kann nicht 1 lang sein)
  begin
    temp := temp shl (6 * (4 - Count));
    temp := temp and $ff00 + temp shl 16 + temp shr 16;
    Output.Write(temp, Count - 1);
  end;
  Output.Size := Output.Position; // Scheint entgegen der Dokumentation TMemoryStream.Memory nicht zu löschen
end;
Janni
2005 PE, 2009 PA, XE2 PA
  Mit Zitat antworten Zitat
Antwort Antwort

 

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 00:47 Uhr.
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz