Beste Weg, um zu finden, die position im Stream, wo bestimmten byte-Sequenz beginnt
Wie denken Sie, was ist der beste Weg zu finden, die position im System.Stream-wo gegeben-byte-Sequenz beginnt (erstes auftreten):
public static long FindPosition(Stream stream, byte[] byteSequence)
{
long position = -1;
///???
return position;
}
P. S. Die einfachste noch die Schnellste Lösung ist bevorzugt. 🙂
- Ihre Frage ist verwirrend...was suchst du? dass bestimmte Folge von bytes in den stream???
- Ich denke, die Frage ist die überschrift sollte aktualisiert werden. Stream ist falsch geschrieben, wie Dampf, die macht es scheinen, wie eine Frage, sollte markiert sein Ventil.
- Eigentlich kam ich zu dieser Frage nur um das zu beheben.
- Ich bin auf der Suche nach guid in den Streams.
- ist der Speicher ein Problem? oder können Sie Lesen Sie den gesamten stream in ein Byte-array?
- Bitte überprüfen, ob meine Lösung passt sich Ihren Bedürfnissen an.
Du musst angemeldet sein, um einen Kommentar abzugeben.
Habe ich erreicht diese Lösung.
Habe ich einige benchmarks mit einer ASCII-Datei, die war
3.050 KB
und38803 lines
.Mit einer Suche
byte
array
von22 bytes
in der letzten Zeile der Datei habe ich das Ergebnis in etwa2.28
Sekunden (bei langsamen/alten Rechner).PadLeftSequence
ist auf der Suche nach dem ersten nicht übereinstimmenden byte, die verursachtSequenceEqual
den Wert false zurück. Es scheint wie eine Mikro-Optimierung zu mir, da würde man erwarten, dassSequenceEqual
zu frühen Rückkehr auf einen nicht-match sowieso. Disclaimer: ich habe nicht getan, alle Messungen, das ist nur Meinung.Behandeln, wenn Sie den stream wie das andere Byte-Reihenfolge, Sie können suchen Sie einfach, wie Sie es Taten, eine Zeichenfolge zu suchen. Wikipedia hat einen tollen Artikel über das. Boyer-Moore ist ein guter und einfacher Algorithmus für diese.
Hier ein schneller hack, den ich zusammen gestellt habe in Java. Es funktioniert und es ist ziemlich nah, wenn nicht von Boyer-Moore. Hoffe es hilft 😉
initBufferSize
variable infindBytes
wird nicht verwendet.Im Grunde müssen Sie halten einen Puffer der gleichen Größe wie
byteSequence
so, dass, sobald Sie haben festgestellt, dass der "nächste byte" in den stream passt, können Sie überprüfen, den rest dann aber noch zurück auf die "übernächste" byte, wenn es nicht eine tatsächliche übereinstimmung.Ist es wahrscheinlich ein bisschen fummelig, was Sie tun, um ehrlich zu sein 🙁
Brauchte ich, diese selbst zu tun, hatte bereits begonnen, und wusste nicht, wie die oben genannten Lösungen. Ich habe ausdrücklich gebraucht, um herauszufinden, wo die Suche-byte-Sequenz endet. In meiner situation brauche ich, um einen schnellen Vorlauf der stream, bis nach, dass die byte-Reihenfolge. Aber Sie können meine Lösung für diese Frage zu:
Hier ist StreamExtensions.cs
Bisschen alt die Frage, aber hier ist meine Antwort. Ich habe festgestellt, dass das Lesen der Blöcke und dann auf der Suche in das ist extrem ineffizient im Vergleich zu nur Lesen ein zu einer Zeit und gehen von dort aus.
Auch, wenn ich mich Recht erinnere, akzeptiert die Antwort ausfallen würde, wenn ein Teil der Sequenz wurde in einem block zu Lesen und die Hälfte in einem anderen - ab, da 12345, Suche für 23, es würde Lesen 12, nicht übereinstimmen, dann Lesen Sie 34 nicht passt, etc... habe es nicht ausprobiert, obwohl, zu sehen, wie es benötigt net 4.0. Auf jeden Fall ist das viel einfacher, und wahrscheinlich deutlich schneller.