Insert / Append und StringBuilder



  • Ich muss einen String zusammenbauen. Die Elemente müssten eigentlich am Anfang eingefügt werden. Nu frage ich mich, was wohl generell schneller ist:

    1. Insert an Position 0
    2. Append und dann Reverse - mit ToString().ToByteArray() + Array.Reverse()



  • Die Frage ist nicht dein Ernst oder?
    Du hast sie dir doch mehr oder weniger schon selbst beantwortet. Alleine wieviele unnötige Funktionsaufrufe du bei deinem 2. Punkt hast, das sollte dich doch stutzig machen oder? Nimm am besten Insert



  • Warum sollte die Frage nicht sein Ernst sein? Würde der StringBuilder das Ganze z.B. als char Array verwalten, dann wäre jede Insert Operation gefolgt vom verschieben der gesamten Daten des bisherigen Arrays. Da kann es sicher performanter sein, immer hinten anzufügen und dann in einem Rutsch das Array umzusortieren.
    Wie immer gilt hier aber die goldene Regel: Wenn es zeitkritischer Code ist, dann miss beide Varianten und nimm die schnellere. Ein "generell schneller" gibt es sehr selten, denn auch ein O(n^3) Algorithmus kann wesentlich schneller sein, als ein O(n) Algorithmus - je nachdem auf welche Daten du ihn anwendest und wie die Konstanten sind.
    Sollte der Code nicht zeitkritisch sein dann nimm lieber den verständlicheren/wartbareren Code.

    KaPtainCugel



  • Weißt du wie lang die Strings werden können sind es immer einzelne Zeichen?

    Wenn beides ja, dann würde ich ein Char-Array nehmen und es von hinten auffüllen und den String(char[], int32, int32)-Konstruktor wählen.



  • @Firefighter
    Ich vermute mal, du hast nicht richtig verstanden, was ich vohabe.

    @KPC / Rhombicosidodecahedron
    Danke erstmal für die Antworten. Ich frage nur, weil ich noch recht frisch in C# / NET bin und noch nicht so richtig weiß, was intern passiert, welche Klasse hat welche Vor/Nachteile, etc.
    Ich werd wohl die Char-Array Variante nehmen, da ich etwa abschätzen kann, wie lang der String wird und es einzelne Zeichen sind.

    Danke euch...



  • Brauchst du den String immer sofort oder kannst du ihn auch erst komplett zusammen sammeln und dann erstellen?

    Wenn ja kannst du alle Strings in einer Liste Sammeln, und sobald danach gefragt wird die Liste umkehren und dann in einem Builder packen 😃

    // Hier im Forum getippter Pseudocode
    public class TextContainer
    {
        public TextContainer()
        {
            _items = new List<string>();
        }
    
        private List<string> _items;
    
        public void Clear()
        {
            _items.Clear();
        }
    
        public void Insert(string text)
        {
            _items.Add(text);
        }
    
        public string BuildText()
        {
            _items.Reverse();
            var builder = new StringBuilder();
            foreach (var text in _items)
                builder.Append(text);
            Clear();
            Insert(text);
            return text;
        }
    }
    
    // Usage
    
    public class Demo
    {
        private TextContainer _container;
    
        public void OnMessageReceived(object sender, MessageEventArgs e) // from an Event
        {
            _container.Insert(e.Text);
        }
    
        public string GetMessages() // As soon the text is needed, get it from the container
        {
            return _container.BuildText();
        }
    }
    


  • Wenn David W. was postet, dann mache ich das auch mal

    public static class Base36
    {
        private const string ALPHABET = "0123456789abcdefghijklmnopqrstuvwxyz";
    
        private const int DECIMAL_CAPACITY = 20;
    
        public static string ToBase36String(Decimal input)
        {
            if (input == 0)
                return "0";
    
            char[] c = new char[DECIMAL_CAPACITY];
    
            Decimal value = input < 0 ? -input : input;
    
            int pos = DECIMAL_CAPACITY;
    
            while (value != 0)
            {
                c[--pos] = ALPHABET[(int)(value % 36)];
                value /= 36;
            }
    
            if (input < 0)
                c[--pos] = '-';
    
            return new String(c, pos, DECIMAL_CAPACITY - pos);
        }
    }
    

    Sollte einer der schnellsten Methoden sein, Base36 zu berechnen.


Anmelden zum Antworten